为什么 isless(0 , Missing) 返回 true 而 0<missing 在 Julia 中返回 Missing ?

Sha*_*yan 3 julia

我今天遇到了 Julia 的奇怪行为,就在那时我试图missing0! 如果你0<missing在 REPL 中尝试这个:

julia> 0<missing
missing
Run Code Online (Sandbox Code Playgroud)

但是如果您尝试使用isless这样的预构建函数:

julia> isless(0 , missing)
true
Run Code Online (Sandbox Code Playgroud)

这很奇怪,因为0<missing意思0 is less than missing与 相同isless(0 , missing)。根据isless文档:

isless(t1::Tuple, t2::Tuple)
当 t1 按字典顺序小于 t2 时返回 true。

不应该也0<missing回来吗?true

Bog*_*ski 5

missing < 0产生是missing因为<是一个“标准”比较运算符。

现在考虑一个问题:missing小于0?答案是:我们不知道。missing代表某个未知值 - 它可以大于或小于0。因此missing < 0产生missing.

正如您在以下文档中看到的<

该运算符实现偏序。

这意味着它不能保证所有值都具有可比性。类似(但不相同)的情况是NaN

julia> NaN < 0.0
false

julia> NaN > 0.0
false

julia> NaN == 0.0
false
Run Code Online (Sandbox Code Playgroud)

另请注意,虽然-0.00.0是不同的浮点值,但我们有:

julia> -0.0 < 0.0
false
Run Code Online (Sandbox Code Playgroud)

现在让我们来讨论一下isless。它是必需的,因为有时您需要一个定义总顺序的运算符,如您在其文档中看到的:

根据固定的全序(与 一起定义)测试是否x小于。yisequal

当您想要确保可以安全地假设每个值都是可比较的时,这非常有用。例如sort使用isless.

现在为了确保isless定义总顺序,我们需要定义如何missing在此总顺序中定位。决定missing比任何其他值都大。因此isless(missing, 0)false. 当然,这是一个任意的决定。它是这样制作的,例如当您将sort 向量missing放在末尾时:

julia> sort([1, missing, 2])
3-element Vector{Union{Missing, Int64}}:
 1
 2
  missing
Run Code Online (Sandbox Code Playgroud)

这是人们通常想要的。

NaN现在注意和的行为-0.0

julia> isless(NaN, missing)
true

julia> isless(Inf, NaN)
true

julia> isless(-0.0, 0.0)
true
Run Code Online (Sandbox Code Playgroud)

正如您所看到的NaN,大于Inf但小于missing并且-0.0小于0.0。再次强调 - 由于isless是全序,因此必须将不同的值放在该全序中的不同位置。