Swift中的import语句是否有相关的成本?

时间:2018-04-04 13:28:36

标签: ios swift swift4

阅读字符串宣言,我看到a paragraph关于在没有必要的情况下避免Foundation导入。

为什么这对Swift团队来说是一个问题?除了美学和代码整洁,进口是否需要付出代价?

导入不必要的框架是否会影响性能,内存使用,打包的应用程序大小或构建时间?

2 个答案:

答案 0 :(得分:5)

您引用的page只是说他们希望看到更多直接构建在Swift中的String方法。目前,一些像区分大小写的字符串比较等任务需要导入Foundation。

好的,我将为你的问题提供一些帮助。答案是它取决于您导入的内容。

查看this answer

  

自Xcode 5以来,有一项新功能引入预编译源数据库。 Xcode 5基本上只编译了所有必需的框架,在数据库中保存了构建,并且在编译代码时已编译的部分使用了

同时查看this question

我们发现在每个使用它的文件中导入UIKit都是必要的。如果上述解决方案正确,则无论导入UIKitFoundation多少次,它都只编译一次。因此,多次导入标准库不会影响编译时间。

但是,第一次导入内容会影响编译时间,因为现在需要在以前不需要时编译该库。

示例如果我必须在一个小的Swift程序中导入Foundation,编译时间将会减慢。说到iOS应用程序,基本上不可能不导入也导入基金会的UIKit,所以我不认为这值得担心,因为每个应用程序都必须编译这些库。

此外,我们需要查看Cocoa PodsCarthage之类的导入:

查看this repo

  

您可以通过两种方式在项目中嵌入第三方依赖项:

     

作为每次执行项目的干净构建时编译的源(示例:CocoaPods,git子模块,复制粘贴代码,应用程序目标所依赖的子项目中的内部库)   作为预构建的框架/库(示例:Carthage,由不想提供源代码的供应商分发的静态库)    CocoaPods是iOS设计中最受欢迎的依赖管理器,导致编译时间更长,因为大多数情况下第三方库的源代码在每次执行干净构建时都会被编译。一般来说,你不应该经常这样做,但实际上,你做(例如因为切换分支,Xcode错误等)。

     

Carthage,即使它更难使用,如果你关心构建时间,也是一个更好的选择。只有当你在依赖列表中更改某些内容时才构建外部依赖项(添加新框架,更新新版本的框架等)。这可能需要5或15分钟才能完成,但与构建嵌入CocoaPods的代码相比,这样做的次数要少得多。

查看this blog

我们看到,如果关注编译时间,可以使用更精确的导入。例如import UIKit.UITableViewController

  

就性能和二进制大小而言, Swift编译器已经在最终二进制文件中优化了任何未使用的符号。如果在编译时没有引用它,则删除它,这意味着导入框架但不使用它的特定部分不应该有任何负面影响。

Another blog州:

  

在这个WWDC 2016 talk中,Apple建议用静态存档替换动态框架以减轻这种影响。为了采用这种方法,我们尽可能静态地重建了许多动态框架,然后将它们合并到一个名为AutomaticCore的单一动态框架中。

     

差异很大:我们的应用程序的发布时间缩短了一半。

TLDR:不值得担心导入像Foundation或UIKit这样的标准内容,它们只编译一次,几乎每个应用都使用它们,因此共享任何性能下降。但是,如果要导入第三方框架,则可能需要使用静态存档来帮助编译时。

答案 1 :(得分:1)

虽然毫无疑问导入框架会增加应用程序的原始文件大小,但它们通常压缩得非常好。如果您需要框架,您别无选择,只能导入它。然而,实际上,文档大小在框架方面不是问题 - 像Mapbox这样相对较大的文件可以包含在您的最终产品的几MB的成本中。这是所有应用程序的共同成本,所以它是一个洗涤。

框架代码也存储在共享库中,而不是存储在可执行文件中,这是一个非常重要的区别。无论您编写哪个Apple平台,请阅读Apple关于框架的OS X文档,因为一般概念是相同的。在其中,它简要地讨论了框架包含和性能之间的关系:

  

如果您担心包含主标头文件可能会导致您的   程序膨胀,不要担心。因为OS X接口已实现   使用框架,这些接口的代码驻留在动态中   共享库,而不是您的可执行文件。另外,只有代码   程序使用的程序在运行时会被加载到内存中,所以你的程序   内存占用同样保持较小。

     

至于在编译期间包含大量头文件,   再一次,不要担心。 Xcode提供了预编译的头文件工具   加快编译时间。通过编译所有框架头文件   一次,除非添加新标题,否则无需重新编译标题   框架。在此期间,您可以使用来自的任何界面   包含很少或没有性能损失的框架。

     

https://developer.apple.com/library/content/documentation/MacOSX/Conceptual/BPFrameworks/Tasks/IncludingFrameworks.html

也就是说,不要导入默认情况下从“伞形”框架导入的框架。例如,导入UIKit会自动导入Foundation,因此请勿导入两者。这真的有所作为吗?不,但关心细节,即使是不重要的细节,也会让某些人陷入其他人想雇用和合作的程序员手中。我不能告诉你我过去曾与多少程序员合作,对这类事情有“谁在乎”的态度。毫不奇怪,他们的代码总是最邋and的,而且他们总是失业。