实例引用真的在 Swift 中有效吗?
Do instance references really work in Swift?
我先写了Objective-C代码
NSMutableString *aStrValue = [NSMutableString stringWithString:@"Hello"];
NSMutableDictionary *aMutDict = [NSMutableDictionary dictionary];
[aMutDict setObject:aStrValue forKey:@"name"];
NSLog(@"Before %@",aMutDict);
[aStrValue appendString:@" World"];
NSLog(@"After %@",aMutDict);
我得到的输出如下
2015-09-17 14:27:21.052 ShareIt[4946:129853] Before {
name = Hello;
}
2015-09-17 14:27:21.057 ShareIt[4946:129853] After {
name = "Hello World";
}
意味着当我将一个字符串附加到一个实际引用到 MutableDictionary 的可变字符串时,更改也会反映在字典中。
但后来我在 Swift
中尝试了相同的方法
var stringValue:String?
stringValue = "Hello"
var dict:Dictionary = ["name":stringValue!]
println(dict)
stringValue! += " World"
stringValue!.extend(" !!!!")
println(dict)
我在操场上看到这样的输出
我的问题是
- 为什么改变的值没有反映在像这样的数据结构中
字典.
- 在 Swift 中添加任何键值是否真的保留了该值或其
参考,如果它保持像 objective-C 这样的参考,那么我的错误是什么?
在swift中,String是一个Struct。
Swift 中的结构不是引用类型,因此当您将其设置为字典时它会被复制。
引用类型
不同的行为取决于您在 Objective-C 代码中使用 NSMutableString
的事实,即 class
。
这意味着 aMutDict
和 aStrValue
是 对同一对象 类型 NSMutableString
的引用。因此,您使用 aStrValue
应用的更改对 aMutDict
可见。
值类型
另一方面,在 Swift 中,您使用的是 String
struct
。这是一个值类型。这意味着当您将值从一个变量复制到另一个变量时,您使用第一个变量所做的更改对第二个变量不可见。
以下示例清楚地描述了 value type
行为:
var word0 = "Hello"
var word1 = word0
word0 += " world" // this will NOT impact word1
word0 // "Hello world"
word1 // "Hello"
希望这对您有所帮助。
Swift 中的字符串(按值复制)与 Objective C 中的字符串(按引用复制)完全不同。
来自 Apple 的 Swift 文档:
Strings Are Value Types
Swift’s String type is a value type. If you create a new String value,
that String value is copied when it is passed to a function or method,
or when it is assigned to a constant or variable. In each case, a new
copy of the existing String value is created, and the new copy is
passed or assigned, not the original version. Value types are
described in Structures and Enumerations Are Value Types.
Swift’s copy-by-default String behavior ensures that when a function
or method passes you a String value, it is clear that you own that
exact String value, regardless of where it came from. You can be
confident that the string you are passed will not be modified unless
you modify it yourself.
Behind the scenes, Swift’s compiler optimizes string usage so that
actual copying takes place only when absolutely necessary. This means
you always get great performance when working with strings as value
types.
我先写了Objective-C代码
NSMutableString *aStrValue = [NSMutableString stringWithString:@"Hello"];
NSMutableDictionary *aMutDict = [NSMutableDictionary dictionary];
[aMutDict setObject:aStrValue forKey:@"name"];
NSLog(@"Before %@",aMutDict);
[aStrValue appendString:@" World"];
NSLog(@"After %@",aMutDict);
我得到的输出如下
2015-09-17 14:27:21.052 ShareIt[4946:129853] Before {
name = Hello;
}
2015-09-17 14:27:21.057 ShareIt[4946:129853] After {
name = "Hello World";
}
意味着当我将一个字符串附加到一个实际引用到 MutableDictionary 的可变字符串时,更改也会反映在字典中。
但后来我在 Swift
中尝试了相同的方法var stringValue:String?
stringValue = "Hello"
var dict:Dictionary = ["name":stringValue!]
println(dict)
stringValue! += " World"
stringValue!.extend(" !!!!")
println(dict)
我在操场上看到这样的输出
我的问题是
- 为什么改变的值没有反映在像这样的数据结构中 字典.
- 在 Swift 中添加任何键值是否真的保留了该值或其 参考,如果它保持像 objective-C 这样的参考,那么我的错误是什么?
在swift中,String是一个Struct。 Swift 中的结构不是引用类型,因此当您将其设置为字典时它会被复制。
引用类型
不同的行为取决于您在 Objective-C 代码中使用 NSMutableString
的事实,即 class
。
这意味着 aMutDict
和 aStrValue
是 对同一对象 类型 NSMutableString
的引用。因此,您使用 aStrValue
应用的更改对 aMutDict
可见。
值类型
另一方面,在 Swift 中,您使用的是 String
struct
。这是一个值类型。这意味着当您将值从一个变量复制到另一个变量时,您使用第一个变量所做的更改对第二个变量不可见。
以下示例清楚地描述了 value type
行为:
var word0 = "Hello"
var word1 = word0
word0 += " world" // this will NOT impact word1
word0 // "Hello world"
word1 // "Hello"
希望这对您有所帮助。
Swift 中的字符串(按值复制)与 Objective C 中的字符串(按引用复制)完全不同。
来自 Apple 的 Swift 文档:
Strings Are Value Types
Swift’s String type is a value type. If you create a new String value, that String value is copied when it is passed to a function or method, or when it is assigned to a constant or variable. In each case, a new copy of the existing String value is created, and the new copy is passed or assigned, not the original version. Value types are described in Structures and Enumerations Are Value Types.
Swift’s copy-by-default String behavior ensures that when a function or method passes you a String value, it is clear that you own that exact String value, regardless of where it came from. You can be confident that the string you are passed will not be modified unless you modify it yourself.
Behind the scenes, Swift’s compiler optimizes string usage so that actual copying takes place only when absolutely necessary. This means you always get great performance when working with strings as value types.