Swift中Self的困惑:结构体内外同名变量的访问问题
Swift结构体内部访问外部同名变量的问题
代码片段
var _message = "Outside Message" struct MyStruct { var _message = "Inside Message" var message: String { mutating get { print(_message) print(self._message) _message = "New Message for Outside" self._message = "New Message for Inside" return self._message } } } var aStruct = MyStruct() print("Result: \(aStruct.message)")
运行输出
Inside Message
Inside Message
Result: New Message for Inside
疑问
为什么在MyStruct内部,使用self与否都只会引用内部的_message变量?如何在message属性中引用外部的_message变量?
解答
1. 为什么_message和self._message都指向内部变量
这是Swift的**作用域遮蔽(Shadowing)**规则导致的:当局部作用域(这里是结构体实例的成员作用域)存在和外部作用域(全局作用域)同名的变量时,局部变量会优先被访问。
self在结构体内部代表当前的实例对象,self._message明确指向实例的成员变量;而直接写_message时,编译器会优先在当前作用域(结构体实例的成员作用域)查找变量,自然也会匹配到内部的_message,所以两者指向的都是同一个内部变量。
2. 如何引用外部的_message
要访问被遮蔽的全局_message,你需要明确指定它的作用域,有两种常用方式:
方式一:通过模块名限定
全局变量默认属于当前模块,在Playground中模块名就是你的Playground文件名(比如你的Playground叫MyPlayground),直接用模块名+变量名即可访问:
mutating get { // 访问全局的_message print(MyPlayground._message) // 访问内部的_message print(self._message) MyPlayground._message = "New Message for Outside" self._message = "New Message for Inside" return self._message }
方式二:封装全局变量到命名空间
把全局变量放到一个自定义的命名空间结构体中,通过静态属性访问,这样更清晰,也不依赖模块名:
// 封装全局变量到命名空间 struct Global { static var _message = "Outside Message" } struct MyStruct { var _message = "Inside Message" var message: String { mutating get { print(Global._message) print(self._message) Global._message = "New Message for Outside" self._message = "New Message for Inside" return self._message } } }
内容的提问来源于stack exchange,提问作者Moshe W
相关产品推荐
相关产品推荐

