如何检查变量是否是julia中的标量

时间:2017-12-11 22:56:07

标签: julia

我想检查变量是否是julia中的标量,例如Integer,String,Number,但不是AstractArray,Tuple,type,struct等。是否有一个简单的方法来执行此操作(即{{1} })

2 个答案:

答案 0 :(得分:6)

在没有更多背景的情况下,标量是或者不是标量的概念是不明确的。 在数学上,定义了标量; (Wikipedia

  

标量是字段的元素,用于定义向量空间

也就是说,在确定某些内容是否是标量(相对于该向量空间)之前,需要根据字段定义向量空间。 对于正确的向量空间,元组可以是标量。

当然,我们并不是在寻找一个数学上严谨的定义。 只是一个务实的。

根据广播认为是标量的

我建议在julia中定义标量的唯一有意义的方式是广播行为。 在Julia 0.7-dev中#23939 我相信这应该简单:

using Base.Broadcast

isscalar(x::T) where T = isscalar(T)
isscalar(::Type{T}) where T = BroadcastStyle(T) isa Broadcast.Scalar

请参阅Broadcast的文档。 Scalar是默认值。所以它基本上是任何没有特定广播行为的东西,即它会敲出像数组和元组等的东西。

在朱莉娅0.6中,这有点混乱,但相似:

isscalar(x::T) where T = isscalar(T)
isscalar(::Type{T}) where T = Base.Broadcast._containertype(T)===Any

使用Broadcast的方法确定某些东西是否是标量,而不是使用自己的方法的优点是,任何一个以标量方式行事的新类型必须确保它能够与那些方法正确 (或者实际上是非标量的,因为标量是默认值。)

结构不是标量

也就是说:有时结构是标量,有时它们不是,它取决于结构。

但请注意,这些方法认为struct是非标量的。 我认为你错了你的愿望。

Julia结构不是(必然或通常)集合类型。 请考虑:BigIntegerBigFloatComplex128等 都使用结构

定义

我很想说使用start方法会使类型成为非标量类型,但由于定义了start(::Number),这种方法会不正确。 (这是debated a few times

答案 1 :(得分:0)

我发现自己需要在MultiResolutionIterators.jl中捕捉最近是否存在标量的概念。

我从other answer找到了基于广播的规则, 不符合我的需要。

特别是我想把字符串视为非标量。

我定义了一个特征, 基于method_exists(start, (T,)), 除了上面提到的例外,例如Number

abstract type Scalarness end
struct Scalar <: Scalarness end
struct NotScalar <: Scalarness end

isscalar(::Type{Any}) = NotScalar() # if we don't know the type we can't really know if scalar or not
isscalar(::Type{<:AbstractString}) = NotScalar() # We consider strings to be nonscalar
isscalar(::Type{<:Number}) = Scalar() # We consider Numbers to be scalar
isscalar(::Type{Char}) = Scalar() # We consider Sharacter to be scalar
isscalar(::Type{T}) where T = method_exists(start, (T,)) ? NotScalar() : Scalar()

类似的事情也由AbstractTrees.jl

完成
isscalar(x) == applicable(start, x) && !isa(x, Integer) && !isa(x, Char) && !isa(x, Task)
相关问题