Julia在数组数组中选择最长数组的最有效方法是什么?

Jar*_*bou 6 arrays max julia

我有一个数组数组,A它是一个N-element Array{Array{Int64,1},1}整数.我正在尝试A使用Julia 找到最大的数组.

例如:

A =  [[1, 2], [3, 4], [5, 6, 7], [1, 2, 5, 8]]
Run Code Online (Sandbox Code Playgroud)

在Python中,我只会这样做:max(A, key=len)但在朱莉娅,我不知道该怎么做.

我做的是这样的:

L = []
for a in A
    push!(L, length(a))
end
A[findmax(L)[2]]
Run Code Online (Sandbox Code Playgroud)

谢谢!

Col*_*ers 6

编辑:注意,也值得查看@crstnbr的其他答案

请考虑以下示例代码:

julia> A = [[1,2], [1,2,3,4,5,6], [1,2,3]]
3-element Array{Array{Int64,1},1}:
 [1, 2]            
 [1, 2, 3, 4, 5, 6]
 [1, 2, 3]         

julia> length(A)
3

julia> length.(A)
3-element Array{Int64,1}:
 2
 6
 3

julia> indmax(length.(A))
2

julia> A[indmax(length.(A))]
6-element Array{Int64,1}:
 1
 2
 3
 4
 5
 6
Run Code Online (Sandbox Code Playgroud)

第一次调用length获取外部向量的长度A,这不是我们想要的.在第二个调用中,我使用广播运算符, .以便我得到每个内部向量的长度.在该indmax行中,我找到了最大值length.(A)的索引,即最长内向量的索引.如果你想要返回最长的内部向量,你可以只A使用行的结果索引indmax.


crs*_*nbr 6

@Colin提供了一个紧凑,方便的答案.但是,如果速度很重要(op要求最有效的方式),这应该接近最佳状态

function findlongest(A)
    idx = 0
    len = 0
    @inbounds for i in 1:length(A)
        l = length(A[i])
        l > len && (idx = i; len=l)
    end
    return A[idx]
end
Run Code Online (Sandbox Code Playgroud)

请注意,这个实现(可能)在Python中是一个非常糟糕的主意:)

快速基准:

julia> using BenchmarkTools

julia> A = [[1,2], [1,2,3,4,5,6], [1,2,3]]
3-element Array{Array{Int64,1},1}:
 [1, 2]            
 [1, 2, 3, 4, 5, 6]
 [1, 2, 3] 

julia> @btime findlongest(A);
  26.880 ns (0 allocations: 0 bytes)

julia> @btime A[indmax(length.(A))];
  9.813 ?s (25 allocations: 1.14 KiB)
Run Code Online (Sandbox Code Playgroud)

这是一个〜365倍的加速比这个例子.

编辑: 更好的基准(评论中建议)

julia> @btime findlongest($A);
  9.813 ns (0 allocations: 0 bytes)

julia> @btime $A[indmax(length.($A))];
  41.813 ns (1 allocation: 112 bytes)
Run Code Online (Sandbox Code Playgroud)

这些$标志避免了设置分配和时间.加速~4.

快速解释

  • for循环在Julia中很快,所以为什么不使用它们
  • 避免分配(length.(A)分配一个新的整数数组)
  • a && b 是"if a then b"的快捷方式
  • @inbounds 避免绑定检查 A[i]