导言
因为项目比较老的缘故,(Google)protobuf的OC版本一直用的是一个古老的实现,也就是使用Builder模式的实现。
例如:
对于这样的一个proto定义:
message MessageA{
required string msg = 1;
}
message MessageB {
required MessageA amsg = 1;
}
创建最顶层结构的代码要这样写
- (void)makePB {
MessageB_Builder *msgbBuilder = [MessageB builder];
MessageA_Builder *msgaBuilder = [MessageA builder];
msgaBuilder.msg = @"the message";
msgbBuilder.amsg = [msgaBuilder build];
MessageB *msgb = [msgbBuilder build];
NSLog(@"%@", msgb.amsg.msg);
}
其builder要从最深层次对象开始创建,逐层向上,思维方式十分的别扭。
于是,想起了GCC的一个扩展语法,貌似挺好用。
- (void)makePBWithGCC {
MessageB_Builder *msgbBuilder = [MessageB builder];
msgbBuilder.amsg = ({
MessageA_Builder *msgaBuilder = [MessageA builder];
msgaBuilder.msg = @"the message";
[msgaBuilder build];
});
MessageB *msgb = [msgbBuilder build];
NSLog(@"%@", msgb.amsg.msg);
}
思维方式依次从上往下,十分舒畅。
用法讲解
这个语法的形式是:({})
,它是GNU C的一个扩展语法(GCC和clang都支持它)。它的执行结果是最后一个语句的值。如果最后一个语句不能被计算出值,那么这个结果是void类型。
具体的语法讲解请参考[Statement Expressions - GCC, the GNU Compiler Collection】(https://gcc.gnu.org/onlinedocs/gcc/Statement-Exprs.html)
疑问
这个语法结构内的变量的生命周期是否和大括号({}
)的等同呢?