【问题标题】:Julia-Lang anonymous vs named function behavior in passing argumentJulia-Lang 匿名与命名函数在传递参数中的行为
【发布时间】:2016-01-01 01:42:18
【问题描述】:

参考 Julia 文档:

在 Julia 中,函数的所有参数都通过引用传递。

当我从匿名函数中获取 Float64 参数的内存地址时,它看起来是正确的。但对于命名函数则不是这样。

test = function (a::Float64)
    println(pointer_from_objref(a));
end
# => (anonymous function)
function test1(a::Float64)
    println(pointer_from_objref(a));
end
# => test1 (generic function with 1 method)
value=0.0;
println(pointer_from_objref(value))
# => Ptr{Void} @0x00007fe797c5c020
test(value)
# => Ptr{Void} @0x00007fe797c5c020
test1(value)
# => Ptr{Void} @0x00007fe799e83960

正如@Gnimuc 提到的,Julia-Lang Doc 中还有一段解释了参数传递行为

Julia 函数参数遵循有时称为的约定 “pass-by-sharing”,这意味着值不会被复制 被传递给函数。函数参数本身充当新的 变量绑定(可以引用值的新位置),但 它们引用的值与传递的值相同。

这种“通过分享”的行为和上面的代码有什么关系吗?

【问题讨论】:

  • AFAIK 函数的所有参数都是通过引用传递的,但数字和字符等纯数据除外。尝试在这些函数中更改您的浮点数......同时您发现了一些与该规则相矛盾的东西。非常有趣的问题。我期待看到答案。
  • 来自doc:“函数参数本身充当新的变量绑定(可以引用值的新位置),但它们引用的值与传递的值相同。”我想知道location 这个词在这里是什么意思。

标签: pointers julia


【解决方案1】:

扩展 Reza 的答案,这里要注意的是“通过共享”推理不适用于不可变对象。如果您尝试相同的代码但使用浮点向量作为参数,您会得到预期的行为,即所有指针都是相同的:

    test = function (a::Vector{Float64})
        println(pointer_from_objref(a));
    end

    # => (anonymous function)
    function test1(a::Vector{Float64})
        println(pointer_from_objref(a));
    end

    # => test1 (generic function with 1 method)
    value=[0.0,0.1];

    println(pointer_from_objref(value))
    # => Ptr{Void} @0x0000000084601be0
    test(value)
    # => Ptr{Void} @0x0000000084601be0
    test1(value)
    # => Ptr{Void} @0x0000000084601be0

【讨论】:

    【解决方案2】:

    pointer_from_objref(object_instance) 函数的 Julia 文档中,我们得到以下描述:

    获取 Julia 对象的内存地址作为 Ptr。的存在 生成的 Ptr 不会保护对象免受垃圾收集, 所以你必须确保整个对象都被引用 Ptr 的使用时间。

    检查以下测试:

    x=10
    y=10
    println(pointer_from_objref(x)) # => Ptr{Void} @0x039ee2c0
    println(pointer_from_objref(y)) # => Ptr{Void} @0x039ee2c0
    

    正如我们所见,pointer_from_objref 无法返回不可变对象的本机地址,这是因为该对象是按值传递的,所以我认为上述问题的答案是 pointer_from_objref 在那里被滥用。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-04-25
      • 2022-11-10
      • 2019-11-23
      • 2011-05-11
      • 1970-01-01
      • 2012-09-10
      相关资源
      最近更新 更多