@import vs #import - iOS 7

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/18947516/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-31 01:33:04  来源:igfitidea点击:

@import vs #import - iOS 7

iosobjective-cimportios7

提问by jamdaddy25

I am playing around with some of the new iOS 7 features and working with some of the Image Effects as discussed in the WWDC video "Implementing Engaging UI on iOS". For producing a blur effect within the source code for the session, UIImagewas extended via a category which imports UIKit like so:

我正在尝试一些新的 iOS 7 功能并使用一些图像效果,如 WWDC 视频“在 iOS 上实现引人入胜的 UI”中所述。为了在会话的源代码中产生模糊效果,UIImage通过导入 UIKit 的类别进行了扩展,如下所示:

@import UIKit;

I think I saw something about this in another session video but I'm having trouble finding it. I'm looking for any background information on when to use this. Can it only be used with Apple frameworks? Are the benefits of using this compiler directive enough that I should go back and update old code?

我想我在另一个会话视频中看到了一些关于此的内容,但我找不到它。我正在寻找有关何时使用它的任何背景信息。它只能与Apple框架一起使用吗?使用这个编译器指令的好处是否足以让我回去更新旧代码?

回答by nevan king

It's a new feature called Modulesor "semantic import". There's more info in the WWDC 2013videos for Session 205and 404. It's kind of a better implementation of the pre-compiled headers. You can use modules with any of the system frameworks in iOS 7 and Mavericks.Modules are a packaging together of the framework executable and it's headers and are touted as being safer and more efficient than #import.

这是一个称为模块或“语义导入”的新功能。Session 205404WWDC 2013视频中有更多信息。这是预编译头文件的更好实现。您可以将模块与 iOS 7 和 Mavericks 中的任何系统框架一起使用。模块是框架可执行文件及其标头的打包在一起,并被吹捧为比.#import

One of the big advantages of using @importis that you don't need to add the framework in the project settings, it's done automatically. That means that you can skip the step where you click the plus button and search for the framework (golden toolbox), then move it to the "Frameworks" group. It will save many developers from the cryptic "Linker error" messages.

使用的一大优点@import不需要在项目设置中添加框架,它是自动完成的。这意味着您可以跳过单击加号按钮并搜索框架(金色工具箱)的步骤,然后将其移至“框架”组。它将使许多开发人员免受神秘的“链接器错误”消息的影响。

You don't actually need to use the @importkeyword.If you opt-in to using modules, all #importand #includedirectives are mapped to use @importautomatically. That means that you don't have to change your source code (or the source code of libraries that you download from elsewhere). Supposedly using modules improves the build performance too, especially if you haven't been using PCHs well or if your project has many small source files.

您实际上并不需要使用@import关键字。如果您选择使用模块,所有#import#include指令都会被映射为@import自动使用。这意味着您不必更改源代码(或从别处下载的库的源代码)。据说使用模块也可以提高构建性能,特别是如果你没有很好地使用 PCH 或者你的项目有很多小源文件。

Modules are pre-built for most Apple frameworks (UIKit, MapKit, GameKit, etc). You can use them with frameworks you create yourself: they are created automatically if you create a Swift framework in Xcode, and you can manually create a ".modulemap" file yourself for any Apple or 3rd-party library.

模块是为大多数 Apple 框架(UIKit、MapKit、GameKit 等)预先构建的。您可以将它们与您自己创建的框架一起使用:如果您在 Xcode 中创建 Swift 框架,它们会自动创建,您可以自己为任何 Apple 或 3rd-party library手动创建“.modulemap”文件。

You can use code-completion to see the list of available frameworks:

您可以使用代码完成来查看可用框架的列表:

enter image description here

在此处输入图片说明

Modules are enabled by default in new projects in Xcode 5. To enable them in an older project, go into your project build settings, search for "Modules" and set "Enable Modules" to "YES". The "Link Frameworks" should be "YES" too:

模块在 Xcode 5 的新项目中默认启用。要在旧项目中启用它们,请进入您的项目构建设置,搜索“模块”并将“启用模块”设置为“是”。“链接框架”也应该是“是”:

You have to be using Xcode 5 and the iOS 7 or Mavericks SDK, but you can still release for older OSs (say iOS 4.3 or whatever). Modules don't change how your code is built or any of the source code.

您必须使用 Xcode 5 和 iOS 7 或 Mavericks SDK,但您仍然可以为较旧的操作系统(例如 iOS 4.3 或其他)发布。模块不会改变您的代码的构建方式或任何源代码。



From the WWDC slides:

来自 WWDC 幻灯片:

  • Imports complete semantic description of a framework
  • Doesn't need to parse the headers
  • Better way to import a framework's interface
  • Loads binary representation
  • More flexible than precompiled headers
  • Immune to effects of local macro definitions (e.g. #define readonly 0x01)
  • Enabled for new projects by default
  • 导入框架的完整语义描述
  • 不需要解析标题
  • 导入框架接口的更好方法
  • 加载二进制表示
  • 比预编译头更灵活
  • 不受局部宏定义的影响(例如#define readonly 0x01
  • 默认为新项目启用


To explicitly use modules:

要显式使用模块:

Replace #import <Cocoa/Cocoa.h>with @import Cocoa;

替换#import <Cocoa/Cocoa.h>@import Cocoa;

You can also import just one header with this notation:

您还可以使用此符号仅导入一个标题:

@import iAd.ADBannerView;

The submodules autocomplete for you in Xcode.

子模块在 Xcode 中为您自动完成。

回答by gbk

Nice answer you can find in book Learning Cocoa with Objective-C (ISBN: 978-1-491-90139-7)

您可以在使用 Objective-C 学习可可一书中找到不错的答案(ISBN:978-1-491-90139-7)

Modules are a new means of including and linking files and libraries into your projects. To understand how modules work and what benefits they have, it is important to look back into the history of Objective-C and the #import statement Whenever you want to include a file for use, you will generally have some code that looks like this:

模块是一种将文件和库包含并链接到项目中的新方法。要了解模块如何工作以及它们有什么好处,重要的是回顾 Objective-C 的历史和 #import 语句每当您​​想要包含一个文件以供使用时,您通常会有一些如下所示的代码:

#import "someFile.h"

Or in the case of frameworks:

或者在框架的情况下:

#import <SomeLibrary/SomeFile.h>

Because Objective-C is a superset of the C programming language, the #import state‐ ment is a minor refinement upon C's #includestatement. The #include statement is very simple; it copies everything it finds in the included file into your code during compilation. This can sometimes cause significant problems. For example, imagine you have two header files: SomeFileA.hand SomeFileB.h; SomeFileA.hincludes SomeFileB.h, and SomeFileB.hincludes SomeFileA.h. This creates a loop, and can confuse the coimpiler. To deal with this, C programmers have to write guards against this type of event from occurring.

因为Objective-C 是C 编程语言的超集,#import 语句是对C#include语句的一个小改进。#include 语句非常简单;它在编译期间将它在包含文件中找到的所有内容复制到您的代码中。这有时会导致严重的问题。例如,假设您有两个头文件:SomeFileA.hSomeFileB.h; SomeFileA.h包括SomeFileB.h,并SomeFileB.h包括SomeFileA.h。这会创建一个循环,并可能混淆编译器。为了解决这个问题,C 程序员必须编写防止此类事件发生的保护措施。

When using #import, you don't need to worry about this issue or write header guards to avoid it. However, #importis still just a glorified copy-and-paste action, causing slow compilation time among a host of other smaller but still very dangerous issues (such as an included file overriding something you have declared elsewhere in your own code.)

使用时#import,您无需担心此问题,也无需编写头保护来避免它。然而,#import它仍然只是一个美化的复制和粘贴操作,在许多其他较小但仍然非常危险的问题中导致编译时间缓慢(例如包含文件覆盖了您在自己的代码中其他地方声明的内容。)

Modules are an attempt to get around this. They are no longer a copy-and-paste into source code, but a serialised representation of the included files that can be imported into your source code only when and where they're needed. By using modules, code will generally compile faster, and be safer than using either #include or #import.

模块试图解决这个问题。它们不再是复制并粘贴到源代码中,而是包含文件的序列化表示,可以仅在需要的时间和地点将其导入到源代码中。通过使用模块,代码通常会编译得更快,并且比使用 #include 或#import.

Returning to the previous example of importing a framework:

回到前面导入框架的例子:

#import <SomeLibrary/SomeFile.h>

To import this library as a module, the code would be changed to:

要将此库作为模块导入,代码将更改为:

@import SomeLibrary;

This has the added bonus of Xcode linking the SomeLibrary framework into the project automatically. Modules also allow you to only include the components you really need into your project. For example, if you want to use the AwesomeObject component in the AwesomeLibrary framework, normally you would have to import everything just to use the one piece. However, using modules, you can just import the specific object you want to use:

这有一个额外的好处,即 Xcode 自动将 SomeLibrary 框架链接到项目中。模块还允许您仅将您真正需要的组件包含到您的项目中。例如,如果您想在 AwesomeLibrary 框架中使用 AwesomeObject 组件,通常您必须导入所有内容才能使用一个。但是,使用模块,您可以只导入要使用的特定对象:

@import AwesomeLibrary.AwesomeObject;

For all new projects made in Xcode 5, modules are enabled by default. If you want to use modules in older projects (and you really should) they will have to be enabled in the project's build settings. Once you do that, you can use both #importand @importstatements in your code together without any concern.

对于在 Xcode 5 中创建的所有新项目,默认情况下启用模块。如果您想在较旧的项目中使用模块(您确实应该这样做),则必须在项目的构建设置中启用它们。一旦你这样做了,你就可以在你的代码中同时使用#importand@import语句而不必担心。

回答by RyanTCB

It currently only works for the built in system frameworks. If you use #importlike apple still do importing the UIKitframework in the app delegate it is replaced (if modules is on and its recognised as a system framework) and the compiler will remap it to be a module import and not an import of the header files anyway. So leaving the #importwill be just the same as its converted to a module import where possible anyway

它目前仅适用于内置系统框架。如果你#import像苹果一样使用仍然UIKit在应用程序委托中导入 框架,它会被替换(如果模块打开并且它被识别为系统框架)并且编译器会将它重新映射为模块导入而不是头文件的导入. 因此,在#import可能的情况下,离开将与将其转换为模块导入相同

回答by loretoparisi

It seems that since XCode 7.x a lot of warnings are coming out when enabling clang module with CLANG_ENABLE_MODULES

似乎由于 XCode 7.xa 在启用 clang 模块时出现了很多警告 CLANG_ENABLE_MODULES

Take a look at Lots of warnings when building with Xcode 7 with 3rd party libraries

使用带有 3rd 方库的 Xcode 7 进行构建时查看大量警告

回答by Julian Król

There is a few benefits of using modules. You can use it only with Apple's framework unless module map is created. @importis a bit similar to pre-compiling headers files when added to .pchfile which is a way to tune app the compilation process. Additionally you do not have to add libraries in the old way, using @importis much faster and efficient in fact. If you still look for a nice reference I will highly recommend you reading this article.

使用模块有几个好处。除非创建了模块映射,否则您只能在 Apple 的框架中使用它。@import添加到.pch文件时有点类似于预编译头文件,这是一种调整应用程序编译过程的方法。此外,您不必以旧方式添加库@import,实际上使用起来更快更高效。如果您仍在寻找不错的参考资料,我强烈建议您阅读这篇文章

回答by yoAlex5

History:

历史:

#include => #import => .pch => @import

#include vs #import
.pch - Precompiled header

#include vs #import
.pch - 预编译头

Module - @import

模块 - @import

Product Name == Product Module Name 

@moduledeclaration says to compiler to load a precompiledbinary of framework which decrease a building time. Modular Framework contains .modulemap[About]

@module声明告诉编译器加载框架的预编译二进制文件,从而减少构建时间。模块化框架包含.modulemap[关于]

If module feature is enabled in Xcode project #includeand #importdirectives are automatically converted to @importthat brings all advantages

如果在 Xcode 项目中启用了模块功能,#include并且#import指令会自动转换为@import这将带来所有优势

enter image description here

在此处输入图片说明