17 6月

Swift语言那些鲜为人知的特性

文 / Russ Bishop:全能型程序员,使用C#,Objective-C和Swift语言编程,开发了奇特的应用Storm Sim Free。

原文链接:http://www.russbishop.net/more-swift-attributes

Swift语言有各种各样缺乏(或没有)文档记录的特性(attribute)放在那里等着被使用。让我们一起看看其中的一些特性:

@inline

这个特性为编译器提供了内联提示。有效的取值是__always和never。除非我认为必须要用这两个值,否则就不会使用它(特别是__always)。到目前为止与其相关的规则还不是很明确,在有限的测试下,它可以正常地工作,但还要视具体情况而定。

进一步的解释:尽管底层虚拟机(Low Level Virtual Machine, LLVM)有强制内联的概念,但我们目前还不知道这个@inline特性是否与其直接映射,也不知道是否存在大小方面的限制,但这将会导致编译器忽略这一点而跳过内联。理论上说应该是这样的,但我不保证一定是。

注意(当优化设置关闭时)在调试模式下的构建将忽略@inline。

@transparent

我最初并未将这个特性列出来。该特性会导致编译器在管道(pipeline)中更早地将函数内联。它用于“像+(Int, Int)这样非常原始的函数”,而“不应该用于独立函数”

甚至在没有优化设置的调试模式下@transparent特性函数就会被内联,所以在调用“1+1”这样的函数的时候并不会特别慢。另外这个特性与@inline(__always)非常类似。

@availability

这个特性可以用来标识某些函数只在某些平台或版本上可用。第一个参数是平台,可以用星号(*)代表一切可用,还可以是iOS或OSX。因为如果需要针对不同的平台,就要指定多个@availability属性。

如果需要表示该函数在某个给定的平台完全不可用时,可以将第二个参数置为unavailable。此外,还可以用introduced,deprecated和obsoleted来指定一个或是多个版本的组合:obsoleted意味着该项已经删除,deprecated仅仅表示如果使用就会给予警告。最后你可以设置message的值,如果该项被使用了就由编译器输出。下面是一些例子:

  1. @availability(*, unavailable)
  2. func foo() {}
  3. @availability(iOS, unavailable, message=“you can’t call this”)
  4. func foo2() {}
  5. @availability(OSX, introduced=10.4, deprecated=10.6, obsoleted=10.10)
  6. @availability(iOS, introduced=5.0, deprecated=7.0)
  7. func foo3() {}

@noreturn

正如该特性所描述的那样:编译器可以假定这个函数是一个永远循环运行的起点,例如while true { },或者假定是函数abort或者exit进程的情况。

评论者Marco Masser指出,如果调用另一个被标志为@noreturn的函数,那么编译器会忽略掉当前函数中缺失的返回值(missing return values),因为编译器理解程序的控制流。

@asmname

该属性给出了函数、方法或属性实现的符号名称。如果你已经知道对应的函数参数及其类型,那么就可以直接调用Swift的内部标准库函数,甚至不用头文件,也可以方便地调用C语言编写的函数:

  1. @asmname(“function”) func f()

@unsafe_no_objc_tagged_pointer

上面这个仍然是个谜,但我猜测它是在告诉Swift与Objective-C联系的时候不要使用tagged pointer

@semantics

这又是另一个谜。参数看起来像是array.mutate_unknown或array.init这样的字符串数组。想必这是要告诉编译器(或静态分析器)函数是如何工作的。

结论

谁还需要乏味老套的 @objc和@autoclosure呢?还是算了吧!

我今年会去参加苹果全球开发者大会(WWDC),你也一定要去呀!

http://www.csdn.net/article/2015-06-08/2824887-more-swift-attributes

08 1月

编程语言易用性最低,却是迄今为止最强大的人机接口

文 / Andrew J.Ko:美国西雅图华盛顿大学信息学院助理教授。

原文链接:http://blogs.uw.edu/ajko/2014/03/25/programming-languages-are-the-least-usable-but-most-powerful-human-computer-interfaces-ever-invented/

这样的说法是真的吗?当自己破译一些神秘的错误信息,调试一些悄无声息的故障,或者给一些没有很好存档的函数提供正确的参数时,我经常会思考。上周我在对一个难以理解的PHP错误信息绞尽脑汁时,把这样的说法发到了推特上。但是,编程语言是否真的易用性差呢?

是还是不是,在推特上仁智所见。但我认为,只有部分缺陷是根本。举例来说,Jakob Nielsen[1]经典的易用性推测法,是关于易用性的一个粗略表征。用户界面其中一个最为突出的问题是缺乏系统状态的可见性:可用的接口应该提供用户输入状态及时和清晰的反馈,以便用户知道系统的状态以及接下来要做什么。当你编写程序时,会发现某个人所编写的指令集与这些指令对应的输出和对周围的影响有很大差异。事实上,即使一个简单的程序也可以有很多分支,也存在一些编写指令集的程序员无法看到的执行路径,而只有后来执行程序的人才能看到。再来说说延迟的反馈!具有复现性的全部文字记录,测试以及调试弥合了程序的命令与执行动作之间的脱节,更好地展现了一个程序执行时的行为。这些工具顶多为程序员认识程序提供了信息,因为程序执行过程固有的复杂性,这种认识需要花费大量的努力。

另一条准则是Nielsen的“系统应该对真实世界进行映射”:系统应当使用用户熟悉的概念,短语和比喻。而使用计算机术语表达思想是编程语言的本份。这可以通过标识符良好的命名,语言范式和结构的选择得到改善。你可能认为编程语言的发展是一个缓慢的过程,因而需要刻意去定义更好的抽象模型语意。但用计算机术语表达事物并不像人类思想那样凌乱和含糊其词。

编程语言可以产出非常实用的工具。事实上,编程语言研究人员向语言添加新的抽象,语义,以及尽力形式化的内容,是为了尽可能减少错误,最大化地使错误信息易于理解,有些人可能会争辩说,编程语言研究人员实际上在做什么?比如静态类型检查就是从根本上提供具体的,可操作的及时反馈。同样,Nielsen的准则“有助于用户认识错误、判断错误并从错误中恢复”已经不是通过语言设计来体现,而是通过精心设计语法高亮显示,源文件结构视图,类层次结构视图等这样的特征来体现。

还有编程语言可能超越图形用户接口易用性的其他易用性原则。举例来说,有什么更好的用户接口比编程语言更能支持撤销,重做和取消操作?当今的文本编辑器和版本控制器中,至少在设计期间,什么样的修改是不能够被撤销,重做或取消的?最优秀的编程语言大概是现有的最一致,灵活,简约和美观的接口了。大多数图形用户接口很难平衡这些设计原则,因为实现这些需要做出牺牲,以更好地适应现实世界。

因此,编程语言在某些方面可能缺乏易用性,但在工具设计中付出一定努力,编程语言可以接近图形界面的易用性。易用性方面的这些改进,能够大大提高易达性(accessibility),易学性(learnability)以及用户的使用效率。

现在来说第二部分:编程语言真的是有史以来发明的最“强大”用户接口吗?这取决于我们对强大的定义。这些编程语言当然是我们拥有的最具表达力用户接口,可以比其他任何用户接口创造出更多东西。

但是如果我们把强大理解为可以直接促进人们的特定目标,那么就会有很多任务,使编程语言变成一种蹩脚的工具。像发送邮件,视频聊天,玩游戏,阅读新闻什么的。这些事情最好由围绕这些活动及其相关概念进行设计的应用程序来支持,而不是由编程语言更低层的抽象来完成。从这个角度讲,编程语言可能是最不强大的用户接口。

如果说这个帖子有什么实在的东西,那么就是其隐含的概念,编程语言只是另一种类型的人机接口,是丰富且多样的用户接口范式设计领域。这里有一些有趣的暗示。例如,程序员也是用户,像HCI(Human-Computer Interaction)研究人员那样,他们一样需要像非程序员使用非编程语言接口那样去思考。在这两个领域我们没有发现更多不同的方法和文化,但问题和相关现象却显著地一致。

对于了解我和我工作的人来说,这些说法应该是不足为奇的。我所有研究的前提是编程语言即用户接口。这就是为什么,尽管我事实上主要学习代码,编码和编码器,但在攻读HCI方向的博士学位,而不是PL(Programming Language),软件工程或者其他一些与这些现象有关的领域。编程语言现在并将永远是我最着迷去学习和改造的一种用户接口。

[1] Web易用性专家,在丹麦科技大学获得了人机交互方向的博士学位。