performance - 如何使用基本技巧来改进我的 Julia 代码?
问题描述
我对 Julia 比较陌生,目前使用的是 1.0 版。我有一个代码,旨在根据输入矩阵生成整数序列。代码在我的机器(i5,双核,16GB 内存)上运行需要 3 个小时,使用 16% 的 CPU 和 3% 的内存。我可以学习和应用任何基本技巧来优化我在 Julia 中的代码以提高其性能吗?缩进对性能有影响吗?是否有可以跟踪我的代码并提出改进建议的包?我在下面提供我的代码。该代码包括一个 R 代码,该代码生成适用于 Julia 代码的数据。如果在 R 代码过程中出现错误,那只是模拟过程中缺乏成就,必须重新运行,直到模拟完成。
using Distances
using RCall
using Distributions
using BSON: @save, @load
using StatsBase
using LinearAlgebra
R"simul<-function(m){
comb<-expand.grid(c(0.01,0.2,0.4),
c(sample(2:7,1),sample(8:12,1),sample(13:20,1)),
c(sample(2:5,1),sample(6:10,1),sample(11:20,1)),
c(150,500,1500))
gener<-function(i){
maxoverlap<-comb[i,1]
nbvar<-comb[i,2]
nbclass<-comb[i,3]
propmix<-runif(1,0.001,1/nbclass)
Q<-MixSim(MaxOmega = maxoverlap, K = nbclass, p = nbvar,PiLow = propmix,resN = 1000)
A <- simdataset(n = comb[i,4], Pi = Q$Pi, Mu = Q$Mu, S = Q$S)
results<-list(Q,A)
return(results)
}
donnees<-sapply(1:nrow(comb),gener)
}
library(MixSim)
donneesimul=simul(1)"
@rget donneesimul
function pointsdpp(t)
datasim=donneesimul[2,t][:X]
Eucldist=pairwise(Euclidean(),transpose(datasim))
D=maximum(Eucldist.^2)
sigma2hat=mean(((Eucldist.^2)./D)[tril!(trues(size((Eucldist.^2)./D)),-1)])
L=exp.(-(Eucldist.^2/D)/(2*sigma2hat))
eigenv=eigvals(L)
prob=eigenv./(eigenv.+1)
eigenvectors=eigvecs(L)
function sampledpp(m)
u=rand(size(L,1))
V=eigenvectors[:,findall(u.<=prob)]
k=size(V,2)
Y=zeros(Int64,k)
for i=k:-1:1
P=sum(V.^2,dims=2)
Pri=P / sum(P)
Cumpri=cumsum(Pri,dims=1)
u=rand()
Y[i]=findfirst(u.<=Cumpri)[1]
if i==1 break end
j=findfirst(V[Y[i],:].!=0)
Vj=V[:,j]
V=V[:,deleteat!(collect(1:1:size(V,2)),j)]
V=V-repeat(Vj,1,size(V,2)).*repeat(transpose(V[Y[i],:]/Vj[Y[i]]),size(V,1))
for a = 1:i-1
for b = 1:a-1
V[:,a] = V[:,a] - transpose(V[:,a])*V[:,b]*V[:,b]
end
V[:,a] = V[:,a] / norm(V[:,a])
end
end
Y=sort(Y)
return(Y)
end
m=collect(1:1000)
sampleY_repet=map(sampledpp,m)
end
w=collect(1:1:81)
echantdpp=map(pointsdpp,w)
@save "echantdppdatasim1.bson" echantdpp
解决方案
在评估 Julia 性能时需要考虑许多问题。虽然您提供的代码远远超出了 MWE(最小工作示例)并且也无法重现。但是,这里有一些一般准则:
- 花一些时间仔细阅读Julia 性能提示并应用它们
- 由于您处理了一些数组,因此您的代码可能会从
@simd
宏中受益。对于像您这样的代码,使用数组视图通常也是一种容易实现的目标。 - 您使用了 16% 的 CPU 功率(可能您有 8 个内核,而您的程序只使用了一个)。考虑使用多线程或多处理——你的程序运行速度会快很多倍
- 对于某些场景,您可能会考虑将 GPU 计算与 Flux.jl 一起使用
- 考虑将您的多核计算迁移到云端(AWS EC2 实例上的 Julia 扩展效果非常好)
由于这些主题中的每一个都是其自身工作的一个大领域,因此您可以一步一步地处理您的代码并提出问题以获得帮助。
推荐阅读
- python - 如何为 Keras 模型编写自定义 dataGenetator
- java - 检查数组是否只是一个字母
- ssl - NSURLConnection sendSynchronousRequest + SSL Pinning
- angular - 当列中有 *ngIf 时,mat-table 中的 ExpressionChangedAfterItHasBeenCheckedError
- javascript - 带有Greensock JS钩子的Vue列表动画:等待离开完成后再进入
- javafx - 如何在 JavaFX 画布中绘制带下划线的文本
- app-inventor - 是否可以在 MIT App Inventor 上编写能够在后台运行的应用程序?
- reactjs - 如何将具有 html 标签的道具内容转换为 html 并将其显示而不是显示为字符串?
- javascript - 在站点地图中指定规则时使用的这个符号 /\ 是什么
- java - 在一组对象中查找连续的字符串属性序列(通过流 API)