Data structures Julia:自引用和递归类型

Data structures Julia:自引用和递归类型,data-structures,struct,julia,self-reference,Data Structures,Struct,Julia,Self Reference,我试图做的不是很直截了当,如果我从结果开始,然后解释我是如何努力达到目标的,也许会更容易 我有一个包含两个字段的结构: struct data{T} point::T mat::Array end 我想做的是嵌套它,并使field mat自引用,以获得如下内容: data{data{Int64}}(data{Int64}(1, [1]), [1]) “外部”类型不应存储[1],而应引用最内部的垫。我不确定这是否有意义,甚至不可能。field mat应重复存储相同的大型阵列 我

我试图做的不是很直截了当,如果我从结果开始,然后解释我是如何努力达到目标的,也许会更容易

我有一个包含两个字段的结构:

struct data{T}
    point::T
    mat::Array
end
我想做的是嵌套它,并使field mat自引用,以获得如下内容:

data{data{Int64}}(data{Int64}(1, [1]), [1])

“外部”类型不应存储[1],而应引用最内部的垫。我不确定这是否有意义,甚至不可能。field mat应重复存储相同的大型阵列

我尝试过这样的方法(n是嵌套类型的数量)

struct data{T}
    point::T
    g::Array
    function D(f, g, n)
        for i = 1:n
            (x = new{T}(f, g); x.f = x)
        end
    end
end 

同样,我也不确定我是否足够了解自引用构造函数,或者这是否可行。如果需要任何帮助/澄清,将不胜感激!

根据您的描述,
数据似乎是一个非常通用的包装器。也许您可以尝试以下方法:

mutable struct Wrap{T}
    w::Wrap{T}
    d::T
    function Wrap(d::T) where T
        w = new{T}()
        w.d = d
        w
    end
end

function Wrap(d, n::Int)
    res = Wrap(d)
    cur = res
    for _ in 1:n-1
        cur.w = Wrap(d)
        cur = cur.w
    end
    res
end

Wrap([1], 4)
# Wrap{Array{Int64,1}}(Wrap{Array{Int64,1}}(Wrap{Array{Int64,1}}(Wrap{Array{Int64,1}}(#undef, [1]), [1]), [1]), [1])

具体模式取决于您想要实现的目标,但以下是一个示例:

struct Data{V, A <: AbstractArray{V}, T} 
    mat::A
    point::T

    Data(mat::A, point::T = nothing) where {V, A <: AbstractArray{V}, T} =
        new{V,A,T}(mat,point)
end
小贴士:

  • 永远不要使用非类型化的容器。因此,当您想要存储
    数组时,您需要在
    结构中定义其类型

  • 使用以大写字母开头的名称表示
    struct
    s

  • 提供构造函数使API可读


  • 最后但并非最不重要的一点。如果您想为这种结构设置多个嵌套级别,编译时间将大大增加。在这种情况下,通常最好使用同质类型。在这种情况下,您可以使用type
    Union
    s代替(在Julia中,少量类型的并集速度很快)

    “外部”类型不应该存储[1],而是引用最里面的mat。”我假设数据中只有一个
    mat
    ,而没有对mat的引用,对吗?@JunTian是的!我在这里将
    w
    定义为
    w::Union{Wrap{T},Nothing}
    。否则,对于有点难看的根元素,它仍然处于
    #unde
    状态。感谢这接近于我所寻找的,但是say Wrap([1],2)的类型应该是:Wrap{Wrap{Int64}(Wrap{Int64}(1,[1]),[1])
    julia> d0 = Data([1,2,3])
    Data{Int64,Array{Int64,1},Nothing}([1, 2, 3], nothing)
    
    julia> d1 = Data([1.0,2.0],d0)
    Data{Float64,Array{Float64,1},Data{Int64,Array{Int64,1},Nothing}}([1.0, 2.0], Data{Int64,Array{Int64,1},Nothing}([1, 2, 3], nothing))