50万奖金+官方证书,深圳国际金融科技大赛正式启动,点击报名 了解详情
写点什么

Scala 语言将加入宏指令

  • 2013-01-22
  • 本文字数:1580 字

    阅读完需:约 5 分钟

Scala 开发团队正在将实验版宏指令加入到即将发行的 2.10 版中。Scala 宏指令提供了编译时元编程的高级形式。 Scala 宏网站描述道:

“宏指令显著简化了代码分析和代码生成,这使得它们成为处理大量现实用例的一种可选工具。传统上涉及编写和维护样板的场合可用宏以简单且易维护的方式实现。因此我们认为宏对于 Scala 编程语言是一项非常有价值的资产。”

Scala 的宏指令允许开发者创建方法时以语法树转化的形式实现。这些是标准方法的定义,其在编译期间被显式地转换。举一个简单的例子,如 assert 方法:

复制代码
import scala.reflect.makro.Context
import language.experimental.macros
object Asserts {
def assert(cond: Boolean, msg: Any) = macro Asserts.assertImpl
def raise(msg: Any) = throw new AssertionError(msg)
def assertImpl(c: Context)(cond: c.Expr[Boolean], msg: c.Expr[Any]): c.Expr[Unit] =
if(assertionsEnabled) c.reify(if(!cond.splice) raise(msg.splice))
else c.reify(())
}

assert 宏就像代码中的一个普通的方法。该实现使用 macro 方法委托成为编译器扩展。该编译器扩展是方法 assertImpl。assertImpl 使用当前编译的上下文作为参数,而参数传给 assert 作为语法树(Expr)。这些语法树接下来被用作产生一个新的语法树并被插入至 assert 宏方法被调用的位置。

对于 assert 宏来说,调用 assert 的方法 assert(x != null, “X is null”) 会给 cond 变量填充 x != null 的语法树而给 msg 变量填充"X is null"的语法树。对 reify 的调用会产生一个 if(x != null) Asserts.raise(“X is null”) 的或者 () 的新语法树。这个语法树会替代原始的 assert(x != null, “X is null”) 调用。

reify 和自清洁宏系统的更多细节可参考自清洁宏建议

有些人怀疑添加宏的效果,在一份题为《 Scala Macros: “Oh God Why?”》博客中, Jay Kreps 评论道:

“这也是我对于 Scala 宏指令的看法(Oh God Why?)。并不是因为宏指令或者这项提议有什么坏处,问题在于这真的是最重要的事情吗?”

Kreps 接下来列举了一系列更重要的事情,包括编译速度、IDE 支持、文档和编译文件大小。

支持 Kreps 观点的大有人在。Ivan Todoroski 在一封给 Scala 邮件列表的信中写到:

“在搜索问题的时候,Scala 宏指令看起来只是一个低级别的、hacking 风格的解决方案。它们在编写时太复杂,不太像 Scala 的风格,调试也麻烦,而且可能不过是为 Scala 的‘太多高深莫测的魔法’的形象增添了一笔。”

对此,Scala 的发明者 Martin Odersky 回复说:

“宏的设计初衷和 Scala 语言的其他一般设计一样,都是为了使事情简单化。我们已经实现通过宏替换代码,希望其他功能也能这样实现。比如说,有一种强推在某种情况下消除 atomic { implicit transaction => … }中的隐含参数和许多其他相关情形。有了宏,这类问题就微不足道了。”

围绕着 Scala 宏的讨论已经逐渐偃旗息鼓,社区成员们正在等着看最终的实现。最终发布的版本始终没有放弃在宏指令方面的冒险。许多社区内基于宏的项目已经逐渐生根发芽,包括:

Macrocosm ——测试宏指令实际用例的库。

Expecty ——Groovy 的 Spock 框架中的断言语句在 Scala 中的适应性改编。

Slick ——引进类似 LINQ 的数据库操作的尝试。Slick 能转化 Scala 语法为数据库查询。

ScalaMock ——Scala 的模拟对象测试库。

2.10.0-M4 发布说明里可以找到其他一系列 Scala2.10 中的功能,包括:

字符串插值

Futures 和 Promises

Value 类

动态类型

隐式类

Scala2.10 版马上就要发布了,Scala 开发团队号召人们试用最新的 milestone 发行版并提供反馈意见。你可以从这里下载最新版本


感谢杨赛对本文的审校。

给InfoQ 中文站投稿或者参与内容翻译工作,请邮件至 editors@cn.infoq.com 。也欢迎大家通过新浪微博( @InfoQ )或者腾讯微博( @InfoQ )关注我们,并与我们的编辑和其他读者朋友交流。

2013-01-22 03:533325
用户头像

发布了 21 篇内容, 共 76161 次阅读, 收获喜欢 1 次。

关注

评论

发布
暂无评论
发现更多内容

ISO-8601 如何解读

HoneyMoose

在线IP地址查询工具

入门小站

工具

oeasy教您玩转vim - 16 - # 行内贴靠

o

【Dubbo3.0技术专题】总体技术体系介绍及技术指南(序章)

码界西柚

dubbo RPC 8月日更 Dubbo3

NDK 使用入门

Changing Lin

8月日更

架构实战营毕业总结

Vic

架构实战营

spring 循环依赖与三级缓存

Rubble

springboot 8月日更

Vue进阶(三十二):npm install、npm install --save与 npm install --save-dev 区别

No Silver Bullet

Vue 8月日更

面向用户的产品进度汇报会

boshi

项目管理 客户

飞书 + Lua 实现企业级组织架构登录认证

K8sCat

lua openresty 网关 飞书 组织架构

「让我们一起Golang」怎样出让协程资源和设置可用CPU核心数

Regan Yue

高并发 协程 Go 语言 8月日更

装机必备的软件里,绝对不能少了这一款 | 剪贴板增强工具

彭宏豪95

效率 工具 windows 实用工具

Swift 仿自如 App 裸眼 3D 效果

fuyoufang

ios swift 8月日更

对数字化的审视思维

boshi

数字化转型

数据库知识整理

十二万伏特皮卡丘

【设计模式】迭代器模式

Andy阿辉

C# 后端 设计模式 8月日更

摸鱼小技巧之IDEA调试篇一

4ye

Java debug 后端 IDEA 8月日更

B 端产品经理如何快速成长?

蒋川

数据产品经理 b端产品经理

与外部系统的读写交互(八)

Databri_AI

flink kafka Cassandra

Django QuerySet 就学那么一点点,一点点就够了

梦想橡皮擦

8月日更

聊聊Java数据类型的那些事

Bob

Java 后端 8月日更

Java 项目还需要 joda 吗

HoneyMoose

rosedb 事务实践

roseduan

数据库 事务 存储 KV存储引擎

架构实战营毕设

Vic

架构实战营

Java实现基于朴素贝叶斯的情感词分析

码农参上

Java 贝叶斯公式 文本情感分析 8月日更

如何做好高并发系统设计

架构精进之路

高并发 8月日更

使用Golang上传文件到MinIO对象存储(一)

liuzhen007

8月日更

你的孩子爱读书吗

箭上有毒

8月日更

Linux之telnet命令

入门小站

Linux

【Flutter 专题】67 图解基本约束 Box (二)

阿策小和尚

Flutter 小菜 0 基础学习 Flutter Android 小菜鸟 8月日更

手撸二叉树之二叉树的中序遍历

HelloWorld杰少

数据结构与算法 8月日更

Scala语言将加入宏指令_Scala_Josh Suereth_InfoQ精选文章