gpt4 book ai didi

julia - 不可变的类型和性能

转载 作者:行者123 更新时间:2023-12-03 20:50:13 24 4
gpt4 key购买 nike

我想知道 Julia 中的不可变类型和性能。

  • 在哪种情况下使复合类型不可变会提高性能?文件说

    They are more efficient in some cases. Types like the Complex example above can be packed efficiently into arrays, and in some cases the compiler is able to avoid allocating immutable objects entirely.



    第二部分实在看不懂。
  • 是否存在使复合类型不可变会降低性能的情况(除了需要通过引用更改字段的情况)?我认为一个例子可能是当一个不可变类型的对象被重复用作参数时,因为

    An object with an immutable type is passed around (both in assignment statements and in function calls) by copying, whereas a mutable type is passed around by reference.



    但是,我在一个简单的例子中找不到任何区别:
    abstract MyType

    type MyType1 <: MyType
    v::Vector{Int}
    end

    immutable MyType2 <: MyType
    v::Vector{Int}
    end


    g(x::MyType) = sum(x.v)

    function f(x::MyType)
    a = zero(Int)
    for i in 1:10_000
    a += g(x)
    end
    return a
    end

    x = fill(one(Int), 10_000)
    x1 = MyType1(x)
    @time f(x1)
    # elapsed time: 0.030698826 seconds (96 bytes allocated)
    x2 = MyType2(x)
    @time f(x2)
    # elapsed time: 0.031835494 seconds (96 bytes allocated)

    那么为什么不是 f不可变类型更慢?是否存在使用不可变类型会使代码变慢的情况?
  • 最佳答案

    不可变类型在它们很小并且完全由直接数据组成时特别快,没有指向堆分配对象的引用(指针)。例如,由两个 Int 组成的不可变类型s 可以潜在地存储在寄存器中,并且根本不存在于内存中。

    知道一个值不会改变也有助于我们优化代码。例如,您访问 x.v在循环内,并且因为 x.v将始终引用相同的向量,我们可以在循环外为其提升负载,而不是在每次迭代时重新加载。但是,您是否从中获得任何好处取决于该负载是否占用了循环中大部分时间。

    在实践中,不可变对象(immutable对象)会降低代码速度的情况很少见,但有两种情况可能会发生。首先,如果你有一个大的不可变类型(比如 100 Int 秒)并且做一些事情,比如对它们的数组进行排序,你需要在其中移动它们很多,额外的复制可能比指向具有引用的对象要慢。其次,不可变对象(immutable对象)最初通常不在堆上分配。如果您需要存储一个堆引用(例如,在 Any 数组中),我们需要将对象移动到堆中。从那里编译器通常不够聪明,无法重用对象的堆分配版本,因此可能会重复复制它。在这种情况下,预先堆分配一个可变对象会更快。

    关于julia - 不可变的类型和性能,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31775391/

    24 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com