首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >在Julia中利用ndgrid/meshgrid功能

在Julia中利用ndgrid/meshgrid功能
EN

Stack Overflow用户
提问于 2017-06-16 04:50:19
回答 3查看 8.7K关注 0票数 8

我试图在Julia中找到类似于MATLAB的meshgridndgrid的功能。我知道朱莉娅在ndgrid中定义了例句,但是当我尝试使用它时,我会得到以下错误。

UndefVarError: ndgrid未定义

有人知道如何让内置的ndgrid函数工作,或者可能知道另一个我还没有找到的函数,或者知道提供这些方法的库(最好使用内置函数)。在这种情况下,我宁愿不写自己的东西。

谢谢!

EN

回答 3

Stack Overflow用户

发布于 2017-06-26 18:30:42

我们倾向于避免这些函数,因为它们分配的数组通常不是必需的。这些数组中的值具有如此规则的结构,不需要存储;它们只需在迭代期间计算。例如,另一种方法是编写数组理解:

代码语言:javascript
运行
复制
julia> [ 10i + j for i=1:5, j=1:5 ]
5×5 Array{Int64,2}:
 11  12  13  14  15
 21  22  23  24  25
 31  32  33  34  35
 41  42  43  44  45
 51  52  53  54  55

或者,您可以编写for循环,或者在product迭代器上迭代:

代码语言:javascript
运行
复制
julia> collect(Iterators.product(1:2, 3:4))
2×2 Array{Tuple{Int64,Int64},2}:
 (1, 3)  (1, 4)
 (2, 3)  (2, 4)
票数 12
EN

Stack Overflow用户

发布于 2020-08-03 05:59:09

我确实发现,有时候在numpy中使用像meshgrid这样的函数是很方便的。通过理解列表很容易做到这一点:

代码语言:javascript
运行
复制
function meshgrid(x, y)
    X = [i for i in x, j in 1:length(y)]
    Y = [j for i in 1:length(x), j in y]
    return X, Y
end

例如:

代码语言:javascript
运行
复制
x = 1:4
y = 1:3
X, Y = meshgrid(x, y)

现在

代码语言:javascript
运行
复制
julia> X
4×3 Array{Int64,2}:
 1  1  1
 2  2  2
 3  3  3
 4  4  4
julia> Y
4×3 Array{Int64,2}:
 1  2  3
 1  2  3
 1  2  3
 1  2  3

但是,我没有发现这使得代码比使用迭代运行得更快。我的意思是:

在定义之后

代码语言:javascript
运行
复制
x = 1:1000
y = x
X, Y = meshgrid(x, y)

我对以下两个函数进行了基准测试

代码语言:javascript
运行
复制
using Statistics

function fun1()
    return mean(sqrt.(X.*X + Y.*Y))
end

function fun2()
    sum = 0.0
    for i in 1:1000
        for j in 1:1000
            sum += sqrt(i*i + j*j)
        end
    end
    return sum / (1000*1000)
end

以下是基准结果:

代码语言:javascript
运行
复制
julia> @btime fun1()
  8.310 ms (19 allocations: 30.52 MiB)
julia> @btime run2()
  1.671 ms (0 allocations: 0 bytes)

meshgrid 方法速度明显较慢,占用了更多的内存。有专家知道原因吗?我知道Julia是一种与Python不同的编译语言,所以迭代不会比矢量化慢,但我不明白为什么向量(数组)计算比迭代慢很多倍。(对于N越大,这种差异就更大了。)

编辑:在阅读了这个职位之后,我有下面的“meshgrid”方法的更新版本。这样做的目的不是事先创建一个网格,而是通过Julia强大的元素数组操作在计算中这样做:

代码语言:javascript
运行
复制
x = collect(1:1000)
y = x'

function fun1v2()
    mean(sqrt.(x .* x .+ y .* y))
end

这里的诀窍是大小-M列数组和大小-N行数组之间的.+,后者返回M-by-N数组。它为你做了“网格”。这个函数比fun1快近3倍,尽管速度不如fun2

代码语言:javascript
运行
复制
julia> @btime fun1v2()
  3.189 ms (24 allocations: 7.63 MiB)
765.8435104896155
票数 3
EN

Stack Overflow用户

发布于 2021-07-02 20:33:34

“上面,”ChrisRackauckas建议,“正确的方法”是与一个懒惰的操作员,但他没有找到它。

现在它中有一个带有惰性ndgrid的注册包:https://github.com/JuliaArrays/LazyGrids.jl

它比VectorizedRoutines.jl中的版本更通用,因为它可以处理不同类型的向量,例如ndgrid(1:3, Float16[0:2], ["x", "y", "z"])

文档中有一些Literate.jl示例,这些示例显示懒散性能非常好。

当然,懒惰的meshgrid离我们只有一步之遥:

meshgrid(y,x) = (ndgrid_lazy(x,y)[[2,1]]...,)

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/44581049

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档