的区别"> 的区别" />
美文网首页
iOS 中 #import "" 和 <> 的区别

iOS 中 #import "" 和 <> 的区别

作者: 高浩浩浩浩浩浩 | 来源:发表于2024-07-18 10:46 被阅读0次

    一般情况下

    我们新建一个项目,再创建一个类文件比如叫FooView,此时我们要在其它地方用到FooView的时候,我们一般这样:

    #import "FooView"
    

    当我使用cocoapod安装第三方库,比如安装了Masonry,那么在用到Masonry的时候,一般是这样子

    #import <Masonry.h>
    

    或者

    #import <Masonry/Masonry.h>
    

    甚至有些时候,你在用 #import <Masonry.h> 的时候还会提示错误:

    image.png

    那究竟什么时候使用 "", 什么时候用<>, 什么时候使用<> 的时候又需要写上路径呢?

    系统SDK

    在开发中的绝大多数场景,我们自己创建的类文件,都是通过#import + "" 的方式去引用的,但是对于系统框架,基本上都是通过#import + <> 的方式。
    那系统的库有什么特殊的么,为什么不能通过""的方式引用呢?

    在stockoverflow上有一个回答:

    " are used for local files. That means files in the current directory or in directories specified by the -iqoute flag for the GCC compiler.
    < and > are used for system files found in the folders of your path. /usr/include is probably one of them. The -I flag can be used to specify more directories to search when looking for those files.

    大意就是
    #import "":

    • 用于包含本地文件(当前目录或通过 -iquote 标志指定的目录)。

    • 常用于项目中的自定义头文件。

    • #import <>:

      • 用于包含系统文件(系统路径中的文件,如 /usr/include)。
      • 常用于标准库文件。
    • GCC 编译器标志:

      • -I:指定搜索头文件的目录。
      • -iquote:指定搜索本地头文件的目录。

    在stackoverflow上看到的另外一个答案是:

    the quoted form is for “local” includes of files (you need to specify the relative path from the current file, e.g. #include “headers/my_header.h”), while the angle-bracket form is for “global” includes — those found somewhere on the include path passed to the compiler。

    大概意思就是双引号用于引用本地文件,需要指定相对路径,尖括号用于全局引用,路径由编译器提供。

    user header map

    Enable the use of Header Maps, which provide the compiler with a mapping from textual header names to their locations, bypassing the normal compiler header search path mechanisms. This allows source code to include headers from various locations in the file system without needing to update the header search path build settings。

    在Xcode项目 - Build Settings 下搜索:search path

    image.png

    我们会看到有一个Use Header Maps开关,默认是打开的。这个意思是:开启这个开关后,在本地会根据当前目录生成一份文件名和相对路径的映射,依靠这个映射,我们可以直接import工程里的文件,不需要依靠header search path。
    我们在管理项目的时候,一般都会把文件放在各个模块下面,模块以各个文件夹区分,在Xcode中创建文件夹会有两种方式,一种是虚拟文件夹(文件还是在项目根目录下),一种是真实文件夹。我之前一直觉得他们就是文件在不在一起的区别,当我关掉Use Header Maps这个选项的时候,这两种文件夹在这里又表现出了不一致。

    该如何解决?

    这时候我们就涉及到Header Search PathsUser Header Search Paths。两者都是提供search path,区别在于一个指明是用户的。并且如果编译器不支持user headers概念,会从header search paths中去寻找。并且看上面有一个Always Search User Paths,但是已经被Deprecated。查阅资料知道

    如果开启,<> 和 “” 都可以引用,关闭的话,user headers 只能通过””引用。

    我们现在要让编译器知道这个文件在哪里,所以要在search paths里面添加引用文件所在的文件夹。 [image:B60806DF-2933-40DB-84F6-C8A9957E7B67-82034-0000F47B21B01244/截屏2020-03-05下午2.20.22.png]

    image.png

    在Header Search Paths里添加的话,无论import “” 还是 import <>都是没有问题的,在User Header Search Paths里添加,只能使用import “”

    解答上面cocopad安装第三方库引用的疑问

    看下面的三种方式

    #import "Masonry.h"
    #import <Masonry.h>
    #import "Masonry/Masonry.h"` </pre>
    

    思考一下这三种方式是否都正确? . . . 答案是:都正确。

    之前一直困惑用哪种方式,又好像哪种方式都正确。这次直接看 search paths下面,发现

    image.png

    cocopod在install的时候,会将第三方库的framework路径添加到Header Search Paths下,所以我们可以直接import,也可以import它的模块下的文件

    总结

    如果按照Xcode默认配置的话,自己新建的文件直接import “”使用,cocoapod安装的第三方库使用import “”、import <>都可以使用。如果关闭Use Header Maps,文件不在根目录下的话,需要手动添加路径到search paths中,添加到User Header Search Paths只能通过import ”“使用,添加到Header Search Paths两种方式都可以。

    参考:
    彻底搞懂import "" 和 import <>
    Xcode-build过程都做了什么

    相关文章

      网友评论

          本文标题:iOS 中 #import "" 和 <> 的区别

          本文链接:https://www.haomeiwen.com/subject/figlhjtx.html