Algorithmically 0.1.6 → 0.1.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: c6b37344d80011486740e722946df13475c44ba5
4
- data.tar.gz: 46afbc8274889d7660acf6fd42f5e3e78260851e
3
+ metadata.gz: 7c3ff69c1deb1ef40a3b013235db5301c5fabe69
4
+ data.tar.gz: 079f3e9fa0f0855bbdff52e73d6047e5a1c8e56d
5
5
  SHA512:
6
- metadata.gz: 1831736b94dc14f2234ebfe1c2ca1c3c33f9d1ff301dd81f070c97bce781e517e38929ba6579467f60fda7093f3d267aa71fc28736850f97ae42c9775c4c75e0
7
- data.tar.gz: a68582cd9aebbb76d27b047643d5160ba6ce1e352e45299512088dfcfbc326d5a8a2f22b58d21006098b1af2b9cdc7701210c7eb481294af92b99504e71e7066
6
+ metadata.gz: 39a4454297e4961ba194fecad4c33c03447b00e702e5411251ccc43dd966fee3d0159af90ad6b9f3887a19788b702427d9239f8ba44b615be9b2e96f35f3cdd1
7
+ data.tar.gz: 3bf6a86a8e384a28438e38ab15cf3d00626fcd38c3cc7b91326b079ee6bb3812eee3f741cffa8e0b3b694f16c97ec0923ed58a1fb046640e59eae3c034a30195
data/README.md CHANGED
@@ -38,4 +38,8 @@ Or install it yourself as:
38
38
 
39
39
  Algorithmically::Neural::GuidedLocalSearch.new(150, [[565,575],[25,185],[345,750],[945,685]], 20, 0.3)
40
40
 
41
+ ### Swarm Algorithms
42
+
43
+ Algorithmically::Swarm::ParticleSwarm.new(2, 100, 1000, 1000, 50, 100.0, 2.0, 2.0)
44
+
41
45
 
@@ -4,10 +4,12 @@ require 'Algorithmically/Neural/perceptron'
4
4
  require 'Algorithmically/Stochastic/random_search'
5
5
  require 'Algorithmically/Stochastic/hill_climbing'
6
6
  require 'Algorithmically/Stochastic/guided_local_search'
7
+ require 'Algorithmically/Swarm/particle_swarm'
7
8
 
8
9
 
9
10
  module Algorithmically
10
11
  include Evolutionary
11
12
  include Neural
12
13
  include Stochastic
14
+ include Swarm
13
15
  end
@@ -0,0 +1,93 @@
1
+ module Algorithmically
2
+ module Swarm
3
+
4
+ class ParticleSwarm
5
+
6
+ def initialize(problem_size, max_gens, search_space, vel_space, pop_size, max_vel, c1, c2)
7
+ @search_space, @vel_space = search_space, vel_space
8
+ @search_space = Array.new(problem_size) {|i| [-5, 5]}
9
+ @vel_space = Array.new(problem_size) {|i| [-1, 1]}
10
+ best = search(max_gens, @search_space, @vel_space, pop_size, max_vel, c1, c2)
11
+ puts "done! Solution: f=#{best[:cost]}, s=#{best[:position].inspect}"
12
+ end
13
+
14
+ def objective_function(vector)
15
+ vector.inject(0.0) { |sum, x| sum + (x ** 2.0) }
16
+ end
17
+
18
+ def random_vector(minmax)
19
+ Array.new(minmax.size) do |i|
20
+ minmax[i][0] + ((minmax[i][1] - minmax[i][0]) * rand())
21
+ end
22
+ end
23
+
24
+ def create_particle(search_space, vel_space)
25
+ particle = {}
26
+ particle[:position] = random_vector(search_space)
27
+ particle[:cost] = objective_function(particle[:position])
28
+ particle[:b_position] = Array.new(particle[:position])
29
+ particle[:b_cost] = particle[:cost]
30
+ particle[:velocity] = random_vector(vel_space)
31
+ particle
32
+ end
33
+
34
+ def get_global_best(population, current_best=nil)
35
+ population.sort! { |x, y| x[:cost] <=> y[:cost] }
36
+ best = population.first
37
+ if current_best.nil? or best[:cost] <= current_best[:cost]
38
+ current_best = {}
39
+ current_best[:position] = Array.new(best[:position])
40
+ current_best[:cost] = best[:cost]
41
+ end
42
+ current_best
43
+ end
44
+
45
+ def update_velocity(particle, gbest, max_v, c1, c2)
46
+ particle[:velocity].each_with_index do |v, i|
47
+ v1 = c1 * rand() * (particle[:b_position][i] - particle[:position][i])
48
+ v2 = c2 * rand() * (gbest[:position][i] - particle[:position][i])
49
+ particle[:velocity][i] = v + v1 + v2
50
+ particle[:velocity][i] = max_v if particle[:velocity][i] > max_v
51
+ particle[:velocity][i] = -max_v if particle[:velocity][i] < -max_v
52
+ end
53
+ end
54
+
55
+ def update_position(part, bounds)
56
+ part[:position].each_with_index do |v, i|
57
+ part[:position][i] = v + part[:velocity][i]
58
+ if part[:position][i] > bounds[i][1]
59
+ part[:position][i]=bounds[i][1]-(part[:position][i]-bounds[i][1]).abs
60
+ part[:velocity][i] *= -1.0
61
+ elsif part[:position][i] < bounds[i][0]
62
+ part[:position][i]=bounds[i][0]+(part[:position][i]-bounds[i][0]).abs
63
+ part[:velocity][i] *= -1.0
64
+ end
65
+ end
66
+ end
67
+
68
+ def update_best_position(particle)
69
+ return if particle[:cost] > particle[:b_cost]
70
+ particle[:b_cost] = particle[:cost]
71
+ particle[:b_position] = Array.new(particle[:position])
72
+ end
73
+
74
+ def search(max_gens, search_space, vel_space, pop_size, max_vel, c1, c2)
75
+ pop = Array.new(pop_size) { create_particle(search_space, vel_space) }
76
+ gbest = get_global_best(pop)
77
+ max_gens.times do |gen|
78
+ pop.each do |particle|
79
+ update_velocity(particle, gbest, max_vel, c1, c2)
80
+ update_position(particle, search_space)
81
+ particle[:cost] = objective_function(particle[:position])
82
+ update_best_position(particle)
83
+ end
84
+ gbest = get_global_best(pop, gbest)
85
+ puts " > gen #{gen+1}, fitness=#{gbest[:cost]}"
86
+ end
87
+ gbest
88
+ end
89
+
90
+ end
91
+
92
+ end
93
+ end
@@ -1,3 +1,3 @@
1
1
  module Algorithmically
2
- VERSION = '0.1.6'
2
+ VERSION = '0.1.7'
3
3
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: Algorithmically
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.6
4
+ version: 0.1.7
5
5
  platform: ruby
6
6
  authors:
7
7
  - popac
@@ -82,6 +82,7 @@ files:
82
82
  - lib/Algorithmically/Stochastic/guided_local_search.rb
83
83
  - lib/Algorithmically/Stochastic/hill_climbing.rb
84
84
  - lib/Algorithmically/Stochastic/random_search.rb
85
+ - lib/Algorithmically/Swarm/particle_swarm.rb
85
86
  - lib/Algorithmically/version.rb
86
87
  homepage: https://github.com/popac/Algorithmically
87
88
  licenses: