我对Julia仍然完全陌生,并对以下行为感到非常烦恼:
immutable X
x::ASCIIString
end
"Foo" == "Foo"
true
X("Foo") == X("Foo")
false
但是使用Int而不是ASCIIString
immutable Y
y::Int
end
3 == 3
true
Y(3) == Y(3)
true
我原本期待
X("Foo") == X("Foo")
是正确的。有人能解释一下为什么不是吗?谢谢。
Julia有两种相等比较方式:
is(x,y)
函数,而用于执行此类比较的等效运算符是===
运算符。棘手的部分在于,如果两个可变对象的内存地址相同,则它们相等,但是当您比较两个不可变对象时,is
在位级别上返回true如果内容相同。2 === 2 #=> true,因为数字是不可变的
"Foo" === "Foo" #=> false
==
运算符或其等效的isequal(x,y)
函数称为通用比较,如果首先存在适用于此类型参数的方法,并且其次该方法返回true,则返回true。那么如果该方法未列出怎么办?然后==
调用===
运算符。==
运算符,因此您实际上调用了===
运算符,并且它检查两个对象是否在位级内容上相同,但它们并不是因为它们引用不同的字符串对象,"Foo" !== "Foo"
编辑:
正如@Andrew所提到的,参考Julia文档,字符串是不可变数据类型,那么为什么"test"!=="true" #=> true
?如果你深入了解字符串数据类型的结构,例如通过xdump("test") #=> ASCIIString data: Array(UInt8,(4,)) UInt8[0x74,0x65,0x73,0x74]
,你会发现字符串是由复合数据类型组成的,其中有一个重要的data
字段。Julia字符串主要是字节序列,存储在字符串类型的data
字段中。并且isimmutable("test".data) #=> false
isimmutable("test") #=> true
,答案需要修改。 - Reza Afzalan==(x1::X,x2::X) = x1.x == x2.x
。我误读了文档(http://julia.readthedocs.org/en/latest/stdlib/base/)中“集合通常通过递归调用所有内容的isequal来实现”的意思,认为这是集合类型的默认实现。但事实上,默认情况下,`X("Foo") == X("Foo")也是
X("Foo") === X("Foo")`。所以再次感谢您提供的非常好的解释。 - vonDonnerstein