Skip to content

Commit 64c8b3f

Browse files
committed
Update ParallelSyncPSOKernel
1 parent 450eecf commit 64c8b3f

File tree

1 file changed

+85
-50
lines changed

1 file changed

+85
-50
lines changed

src/solve.jl

Lines changed: 85 additions & 50 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,56 @@ function SciMLBase.init(
3535
prob, opt, particles, init_gbest)
3636
end
3737

38+
function SciMLBase.init(
39+
prob::OptimizationProblem, opt::ParallelPSOKernel, args...; kwargs...)
40+
backend = opt.backend
41+
@assert prob.u0 isa SArray
42+
43+
## Bounds check
44+
lb, ub = check_init_bounds(prob)
45+
lb, ub = check_init_bounds(prob)
46+
prob = remake(prob; lb = lb, ub = ub)
47+
48+
particles = KernelAbstractions.allocate(
49+
backend, SPSOParticle{typeof(prob.u0), eltype(typeof(prob.u0))}, opt.num_particles)
50+
kernel! = gpu_init_particles!(backend)
51+
52+
kernel!(particles, prob, opt, typeof(prob.u0); ndrange = opt.num_particles)
53+
54+
best_particle = minimum(particles)
55+
_init_gbest = SPSOGBest(best_particle.best_position, best_particle.best_cost)
56+
57+
init_gbest = KernelAbstractions.allocate(backend, typeof(_init_gbest), (1,))
58+
copyto!(init_gbest, [_init_gbest])
59+
return PSOCache{
60+
typeof(prob), typeof(opt), typeof(particles), typeof(init_gbest)}(
61+
prob, opt, particles, init_gbest)
62+
end
63+
64+
function SciMLBase.init(
65+
prob::OptimizationProblem, opt::ParallelSyncPSOKernel, args...; kwargs...)
66+
backend = opt.backend
67+
@assert prob.u0 isa SArray
68+
69+
## Bounds check
70+
lb, ub = check_init_bounds(prob)
71+
lb, ub = check_init_bounds(prob)
72+
prob = remake(prob; lb = lb, ub = ub)
73+
74+
particles = KernelAbstractions.allocate(
75+
backend, SPSOParticle{typeof(prob.u0), eltype(typeof(prob.u0))}, opt.num_particles)
76+
kernel! = gpu_init_particles!(backend)
77+
78+
kernel!(particles, prob, opt, typeof(prob.u0); ndrange = opt.num_particles)
79+
80+
best_particle = minimum(particles)
81+
init_gbest = SPSOGBest(best_particle.best_position, best_particle.best_cost)
82+
83+
return PSOCache{
84+
typeof(prob), typeof(opt), typeof(particles), typeof(init_gbest)}(
85+
prob, opt, particles, init_gbest)
86+
end
87+
3888
function SciMLBase.reinit!(cache::PSOCache; kwargs...)
3989
reinit_cache!(cache, cache.alg)
4090
end
@@ -55,6 +105,23 @@ function reinit_cache!(cache::PSOCache, opt::ParallelPSOKernel)
55105
return nothing
56106
end
57107

108+
function reinit_cache!(cache::PSOCache, opt::ParallelSyncPSOKernel)
109+
prob = cache.prob
110+
backend = opt.backend
111+
particles = cache.particles
112+
113+
kernel! = PSOGPU.gpu_init_particles!(backend)
114+
kernel!(particles, prob, opt, typeof(prob.u0); ndrange = opt.num_particles)
115+
116+
best_particle = minimum(particles)
117+
118+
init_gbest = SPSOGBest(best_particle.best_position, best_particle.best_cost)
119+
120+
cache.gbest = init_gbest
121+
122+
return nothing
123+
end
124+
58125
function SciMLBase.solve!(cache, args...; maxiters = 100, kwargs...)
59126
solve!(cache, cache.alg, args...; maxiters, kwargs...)
60127
end
@@ -78,6 +145,24 @@ function SciMLBase.solve!(
78145
stats = Optimization.OptimizationStats(; time = t1 - t0))
79146
end
80147

148+
function SciMLBase.solve!(
149+
cache::PSOCache, opt::ParallelSyncPSOKernel, args...; maxiters = 100, kwargs...)
150+
prob = cache.prob
151+
t0 = time()
152+
gbest, particles = vectorized_solve!(prob,
153+
init_gbest,
154+
gpu_particles,
155+
opt,
156+
args...;
157+
kwargs...)
158+
t1 = time()
159+
160+
particles_positions = get_pos.(particles)
161+
SciMLBase.build_solution(SciMLBase.DefaultOptimizationCache(prob.f, prob.p), opt,
162+
gbest.position, prob.f(gbest.position, prob.p), original = particles_positions,
163+
stats = Optimization.OptimizationStats(; time = t1 - t0))
164+
end
165+
81166
function SciMLBase.solve(prob::OptimizationProblem, opt::ParallelPSOKernel,
82167
args...; maxiters = 100, kwargs...)
83168
solve!(init(prob, opt, args...; maxiters, kwargs...), opt)
@@ -99,34 +184,6 @@ function SciMLBase.__solve(prob::OptimizationProblem,
99184
stats = Optimization.OptimizationStats(; time = solve_time))
100185
end
101186

102-
function pso_solve(prob::OptimizationProblem,
103-
opt::ParallelPSOKernel,
104-
args...;
105-
kwargs...)
106-
backend = opt.backend
107-
@assert prob.u0 isa SArray
108-
init_gbest, particles = init_particles(prob, opt, typeof(prob.u0))
109-
# TODO: Do the equivalent of cu()/roc()
110-
particles_eltype = eltype(particles) === Float64 ? Float32 : eltype(particles)
111-
gpu_particles = KernelAbstractions.allocate(backend,
112-
particles_eltype,
113-
size(particles))
114-
copyto!(gpu_particles, particles)
115-
gpu_init_gbest = KernelAbstractions.allocate(backend, typeof(init_gbest), (1,))
116-
copyto!(gpu_init_gbest, [init_gbest])
117-
118-
t0 = time()
119-
gbest, particles = vectorized_solve!(prob,
120-
gpu_init_gbest,
121-
gpu_particles,
122-
opt,
123-
Val(opt.global_update),
124-
args...;
125-
kwargs...)
126-
t1 = time()
127-
gbest, particles, t1 - t0
128-
end
129-
130187
function pso_solve(prob::OptimizationProblem,
131188
opt::ParallelPSOArray,
132189
args...;
@@ -150,25 +207,3 @@ function pso_solve(prob::OptimizationProblem, opt::SerialPSO, args...; kwargs...
150207
t1 = time()
151208
gbest, particles, t1 - t0
152209
end
153-
154-
function pso_solve(prob::OptimizationProblem,
155-
opt::ParallelSyncPSOKernel,
156-
args...;
157-
kwargs...)
158-
backend = opt.backend
159-
init_gbest, particles = init_particles(prob, opt, typeof(prob.u0))
160-
particles_eltype = eltype(particles) === Float64 ? Float32 : eltype(particles)
161-
gpu_particles = KernelAbstractions.allocate(backend, particles_eltype, size(particles))
162-
copyto!(gpu_particles, particles)
163-
init_gbest = init_gbest
164-
165-
t0 = time()
166-
gbest, particles = vectorized_solve!(prob,
167-
init_gbest,
168-
gpu_particles,
169-
opt,
170-
args...;
171-
kwargs...)
172-
t1 = time()
173-
gbest, particles, t1 - t0
174-
end

0 commit comments

Comments
 (0)