y_petri 2.0.2 → 2.0.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/lib/y_petri/manipulator/hash_key_pointer.rb +38 -0
- data/lib/y_petri/manipulator/petri_net_related_methods.rb +55 -0
- data/lib/y_petri/manipulator/selection.rb +11 -0
- data/lib/y_petri/manipulator/simulation_related_methods.rb +361 -0
- data/lib/y_petri/manipulator.rb +9 -587
- data/lib/y_petri/net.rb +65 -106
- data/lib/y_petri/simulation.rb +28 -9
- data/lib/y_petri/timed_simulation.rb +10 -3
- data/lib/y_petri/transition.rb +13 -28
- data/lib/y_petri/version.rb +2 -1
- data/lib/y_petri/workspace/petri_net_related_methods.rb +88 -0
- data/lib/y_petri/workspace/{instance_methods.rb → simulation_related_methods.rb} +7 -80
- data/lib/y_petri/workspace.rb +8 -8
- data/lib/y_petri.rb +29 -58
- data/test/y_petri_test.rb +38 -43
- metadata +9 -6
- data/test/y_petri_graph.png +0 -0
data/lib/y_petri/net.rb
CHANGED
@@ -28,9 +28,9 @@ class YPetri::Net
|
|
28
28
|
# <em>false</em> if the place is already included in the net.
|
29
29
|
#
|
30
30
|
def include_place! place
|
31
|
-
|
32
|
-
return false if @places.include?
|
33
|
-
@places <<
|
31
|
+
pl = place( place )
|
32
|
+
return false if @places.include? pl
|
33
|
+
@places << pl
|
34
34
|
return true
|
35
35
|
end
|
36
36
|
|
@@ -40,12 +40,12 @@ class YPetri::Net
|
|
40
40
|
# already in the net.
|
41
41
|
#
|
42
42
|
def include_transition! transition;
|
43
|
-
|
44
|
-
return false if @transitions.include?
|
45
|
-
raise TypeError, "Unable to include the transition #{
|
43
|
+
tr = transition( transition )
|
44
|
+
return false if @transitions.include? tr
|
45
|
+
raise TypeError, "Unable to include the transition #{tr} in #{self}: " +
|
46
46
|
"It connects to one or more places outside the net." unless
|
47
|
-
|
48
|
-
@transitions <<
|
47
|
+
tr.arcs.all? { |pl| include? pl }
|
48
|
+
@transitions << tr
|
49
49
|
return true
|
50
50
|
end
|
51
51
|
|
@@ -55,10 +55,10 @@ class YPetri::Net
|
|
55
55
|
# net connect to it.
|
56
56
|
#
|
57
57
|
def exclude_place! place
|
58
|
-
|
59
|
-
raise "Unable to exclude #{
|
60
|
-
"depend on it" if transitions.any? { |
|
61
|
-
return true if @places.delete
|
58
|
+
pl = place( place )
|
59
|
+
raise "Unable to exclude #{pl} from #{self}: One or more transitions" +
|
60
|
+
"depend on it" if transitions.any? { |tr| tr.arcs.include? pl }
|
61
|
+
return true if @places.delete pl
|
62
62
|
return false
|
63
63
|
end
|
64
64
|
|
@@ -66,8 +66,8 @@ class YPetri::Net
|
|
66
66
|
# <em>false</em> if the transition was not found in the net.
|
67
67
|
#
|
68
68
|
def exclude_transition! transition
|
69
|
-
|
70
|
-
return true if @transitions.delete
|
69
|
+
tr = transition( transition )
|
70
|
+
return true if @transitions.delete tr
|
71
71
|
return false
|
72
72
|
end
|
73
73
|
|
@@ -92,18 +92,18 @@ class YPetri::Net
|
|
92
92
|
# Inquirer whether the net includes a place / transition.
|
93
93
|
#
|
94
94
|
def include? place_or_transition
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
return places.include?
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
return transitions.include?
|
95
|
+
pl = begin
|
96
|
+
place( place_or_transition )
|
97
|
+
rescue NameError
|
98
|
+
nil
|
99
|
+
end
|
100
|
+
return places.include? pl if pl
|
101
|
+
tr = begin
|
102
|
+
transition( place_or_transition )
|
103
|
+
rescue NameError
|
104
|
+
nil
|
105
|
+
end
|
106
|
+
return transitions.include? tr if tr
|
107
107
|
return false
|
108
108
|
end
|
109
109
|
|
@@ -336,94 +336,53 @@ class YPetri::Net
|
|
336
336
|
|
337
337
|
def visualize
|
338
338
|
require 'graphviz'
|
339
|
-
γ = GraphViz.new :G
|
340
|
-
|
341
|
-
|
342
|
-
|
343
|
-
|
344
|
-
|
345
|
-
|
346
|
-
|
347
|
-
|
348
|
-
|
349
|
-
|
350
|
-
|
351
|
-
|
352
|
-
|
353
|
-
|
354
|
-
|
355
|
-
|
356
|
-
|
357
|
-
|
358
|
-
#
|
359
|
-
|
360
|
-
|
361
|
-
|
362
|
-
|
363
|
-
# g.edge[:dir] = "forward"
|
364
|
-
# g.edge[:arrowsize] = "0.5"
|
365
|
-
|
366
|
-
# add place nodes
|
367
|
-
place_nodes =
|
368
|
-
Hash[ places.zip places.map { |p|
|
369
|
-
γ.add_nodes p.name.to_s, fillcolor: 'lightgrey', color: 'grey', style: 'filled'
|
370
|
-
} ]
|
371
|
-
|
372
|
-
# add transition nodes
|
373
|
-
transition_nodes =
|
374
|
-
Hash[ transitions.zip transitions.map { |t|
|
375
|
-
γ.add_nodes( t.name.to_s,
|
376
|
-
shape: 'box',
|
377
|
-
fillcolor: if t.assignment? then 'yellow'
|
378
|
-
elsif t.basic_type == :SR then 'lightcyan'
|
379
|
-
else 'ghostwhite' end,
|
380
|
-
color: if t.assignment? then 'goldenrod'
|
381
|
-
elsif t.basic_type == :SR then 'cyan'
|
382
|
-
else 'grey' end,
|
383
|
-
style: 'filled'
|
384
|
-
)
|
385
|
-
|
386
|
-
} ]
|
387
|
-
|
388
|
-
# add edges
|
389
|
-
transition_nodes.each { |t, t_node|
|
390
|
-
if t.assignment? then
|
391
|
-
t.codomain.each { |p|
|
392
|
-
γ.add_edges t_node, place_nodes[p], color: 'goldenrod'
|
339
|
+
γ = GraphViz.new :G
|
340
|
+
# Add places and transitions.
|
341
|
+
place_nodes = places.map.with_object Hash.new do |pl, ꜧ|
|
342
|
+
ꜧ[pl] = γ.add_nodes pl.name.to_s,
|
343
|
+
fillcolor: 'lightgrey',
|
344
|
+
color: 'grey',
|
345
|
+
style: 'filled'
|
346
|
+
end
|
347
|
+
transition_nodes = transitions.map.with_object Hash.new do |tr, ꜧ|
|
348
|
+
ꜧ[tr] = γ.add_nodes tr.name.to_s,
|
349
|
+
shape: 'box',
|
350
|
+
fillcolor: if tr.assignment? then 'yellow'
|
351
|
+
elsif tr.basic_type == :SR then 'lightcyan'
|
352
|
+
else 'ghostwhite' end,
|
353
|
+
color: if tr.assignment? then 'goldenrod'
|
354
|
+
elsif tr.basic_type == :SR then 'cyan'
|
355
|
+
else 'grey' end,
|
356
|
+
style: 'filled'
|
357
|
+
end
|
358
|
+
# Add Petri net arcs.
|
359
|
+
transition_nodes.each { |tr, tr_node|
|
360
|
+
if tr.assignment? then
|
361
|
+
tr.codomain.each { |pl|
|
362
|
+
γ.add_edges tr_node, place_nodes[pl], color: 'goldenrod'
|
393
363
|
}
|
394
|
-
(
|
395
|
-
γ.add_edges
|
364
|
+
( tr.domain - tr.codomain ).each { |pl|
|
365
|
+
γ.add_edges tr_node, place_nodes[pl], color: 'grey', arrowhead: 'none'
|
396
366
|
}
|
397
|
-
elsif
|
398
|
-
|
399
|
-
if
|
400
|
-
γ.add_edges
|
401
|
-
elsif
|
402
|
-
γ.add_edges place_nodes[
|
367
|
+
elsif tr.basic_type == :SR then
|
368
|
+
tr.codomain.each { |pl|
|
369
|
+
if tr.stoichio[pl] > 0 then # producing arc
|
370
|
+
γ.add_edges tr_node, place_nodes[pl], color: 'cyan'
|
371
|
+
elsif tr.stoichio[pl] < 0 then # consuming arc
|
372
|
+
γ.add_edges place_nodes[pl], tr_node, color: 'cyan'
|
403
373
|
else
|
404
|
-
γ.add_edges place_nodes[
|
374
|
+
γ.add_edges place_nodes[pl], tr_node, color: 'grey', arrowhead: 'none'
|
405
375
|
end
|
406
376
|
}
|
407
|
-
(
|
408
|
-
γ.add_edges
|
377
|
+
( tr.domain - tr.codomain ).each { |pl|
|
378
|
+
γ.add_edges tr_node, place_nodes[pl], color: 'grey', arrowhead: 'none'
|
409
379
|
}
|
410
380
|
end
|
411
381
|
}
|
412
|
-
|
413
|
-
|
414
|
-
#
|
415
|
-
|
416
|
-
# node = nodes[ place_name ]
|
417
|
-
# next unless set_of_places.map { |ɴ, _| ɴ }.include?( upstream_place.name )
|
418
|
-
# next if upstream_place == place_instance
|
419
|
-
# upstream_node = nodes[ upstream_place.name ]
|
420
|
-
# node << upstream_node
|
421
|
-
# }
|
422
|
-
# }
|
423
|
-
|
424
|
-
# Generate output image
|
425
|
-
γ.output png: "y_petri_graph.png"
|
426
|
-
YSupport::KDE.show_file_with_kioclient File.expand_path( '.', "y_petri_graph.png" )
|
382
|
+
# Generate output image.
|
383
|
+
γ.output png: File.expand_path( "~/y_petri_graph.png" )
|
384
|
+
# require 'y_support/kde'
|
385
|
+
YSupport::KDE.show_file_with_kioclient File.expand_path( "~/y_petri_graph.png" )
|
427
386
|
end
|
428
387
|
|
429
388
|
# Inspect string of the instance.
|
data/lib/y_petri/simulation.rb
CHANGED
@@ -30,6 +30,14 @@ class YPetri::Simulation
|
|
30
30
|
attr_reader :recording
|
31
31
|
alias :r :recording
|
32
32
|
|
33
|
+
# Zero marking vector.
|
34
|
+
#
|
35
|
+
attr_reader :zero_ᴍ
|
36
|
+
|
37
|
+
# Zero gradient.
|
38
|
+
#
|
39
|
+
attr_reader :zero_gradient
|
40
|
+
|
33
41
|
# Simulation settings.
|
34
42
|
#
|
35
43
|
def settings; {} end
|
@@ -141,13 +149,14 @@ class YPetri::Simulation
|
|
141
149
|
|
142
150
|
@assignment_closures_for_A = create_assignment_closures_for_A
|
143
151
|
|
144
|
-
@zero_ᴍ = Matrix.zero( free_places.size, 1 )
|
145
|
-
|
146
152
|
puts "other assets set up, about to reset" if YPetri::DEBUG
|
147
153
|
|
148
154
|
# ----------- Reset -------------
|
149
155
|
reset!
|
150
156
|
|
157
|
+
@zero_ᴍ = compute_initial_marking_vector_of_free_places.map { |e| e * 0 }
|
158
|
+
@zero_gradient = @zero_ᴍ.dup
|
159
|
+
|
151
160
|
puts "reset complete" if YPetri::DEBUG
|
152
161
|
end
|
153
162
|
|
@@ -777,7 +786,7 @@ class YPetri::Simulation
|
|
777
786
|
# State differential for sR transitions.
|
778
787
|
#
|
779
788
|
def gradient_for_sR
|
780
|
-
rate_closures_for_sR.map( &:call ).reduce( @
|
789
|
+
rate_closures_for_sR.map( &:call ).reduce( @zero_gradient, :+ )
|
781
790
|
end
|
782
791
|
|
783
792
|
# State differential for sR transitions as a hash { place_name: ∂ / ∂ᴛ }.
|
@@ -1059,25 +1068,35 @@ class YPetri::Simulation
|
|
1059
1068
|
#
|
1060
1069
|
def reset!
|
1061
1070
|
puts "Starting #reset! method" if YPetri::DEBUG
|
1062
|
-
|
1063
|
-
zero_vector = Matrix.column_vector( places.map { 0 } ) # Float zeros
|
1064
|
-
puts "zero vector prepared" if YPetri::DEBUG
|
1071
|
+
|
1065
1072
|
mv_clamped = compute_marking_vector_of_clamped_places
|
1066
1073
|
puts "#reset! obtained marking vector of clamped places" if YPetri::DEBUG
|
1067
1074
|
clamped_component = C2A() * mv_clamped
|
1068
1075
|
puts "clamped component of marking vector prepared:\n#{clamped_component}" if YPetri::DEBUG
|
1076
|
+
|
1069
1077
|
mv_free = compute_initial_marking_vector_of_free_places
|
1070
1078
|
puts "#reset! obtained initial marking vector of free places" if YPetri::DEBUG
|
1071
1079
|
free_component = F2A() * mv_free
|
1072
1080
|
puts "free component of marking vector prepared:\n#{free_component}" if YPetri::DEBUG
|
1081
|
+
|
1082
|
+
# zero_vector = Matrix.column_vector( places.map { SY::ZERO rescue 0 } ) # Float zeros
|
1083
|
+
zero_vector = Matrix.column_vector( places.map { 0 } ) # Float zeros
|
1084
|
+
puts "zero vector prepared: #{zero_vector}" if YPetri::DEBUG
|
1085
|
+
|
1073
1086
|
free_component.aT { |v|
|
1074
1087
|
qnt = v.first.quantity rescue :no_quantity
|
1075
1088
|
unless qnt == :no_quantity
|
1076
1089
|
v.all? { |e| e.quantity == qnt }
|
1077
1090
|
else true end
|
1078
|
-
}
|
1079
|
-
puts "free component of marking vector
|
1080
|
-
|
1091
|
+
} if YPetri::DEBUG
|
1092
|
+
puts "free component of marking vector checked" if YPetri::DEBUG
|
1093
|
+
|
1094
|
+
@marking_vector = free_component + clamped_component
|
1095
|
+
# Matrix
|
1096
|
+
# .column_vector( places.map.with_index do |_, i|
|
1097
|
+
# clamped_component[i, 0] || free_component[i, 0]
|
1098
|
+
# end )
|
1099
|
+
|
1081
1100
|
puts "marking vector assembled\n#{m}\n, about to reset recording" if YPetri::DEBUG
|
1082
1101
|
reset_recording!
|
1083
1102
|
puts "reset recording done, about to initiate sampling process" if YPetri::DEBUG
|
@@ -87,8 +87,9 @@ class YPetri::TimedSimulation < YPetri::Simulation
|
|
87
87
|
@sampling_period = args.delete :sampling_period
|
88
88
|
@target_time = args.delete :target_time
|
89
89
|
@initial_time = args.delete( :initial_time ) ||
|
90
|
-
@target_time.nil? ? nil : @target_time.class.zero
|
90
|
+
@target_time.nil? ? nil : @sampling_period * 0 # @target_time.class.zero
|
91
91
|
super args
|
92
|
+
@zero_gradient = @zero_ᴍ.map { |e| step_size.to_f / step_size * e }
|
92
93
|
end
|
93
94
|
# LATER: transition clamps
|
94
95
|
|
@@ -113,7 +114,12 @@ class YPetri::TimedSimulation < YPetri::Simulation
|
|
113
114
|
# Scalar field gradient for free places.
|
114
115
|
#
|
115
116
|
def gradient_for_free_places
|
116
|
-
|
117
|
+
g_sR = gradient_for_sR
|
118
|
+
if g_sR then
|
119
|
+
S_for_SR() * flux_vector_for_SR + g_sR
|
120
|
+
else
|
121
|
+
S_for_SR() * flux_vector_for_SR
|
122
|
+
end
|
117
123
|
end
|
118
124
|
|
119
125
|
# Gradient for free places as a hash { place_name: ∂ / ∂ᴛ }.
|
@@ -133,7 +139,8 @@ class YPetri::TimedSimulation < YPetri::Simulation
|
|
133
139
|
#
|
134
140
|
def Δ_Euler_for_free_places( Δt=step_size )
|
135
141
|
# Here, ∂ represents all R transitions, to which TSr and Tsr are added:
|
136
|
-
gradient_for_free_places * Δt
|
142
|
+
g_free = gradient_for_free_places * Δt
|
143
|
+
g_free + Δ_for_TSr( Δt ) + Δ_for_Tsr( Δt )
|
137
144
|
end
|
138
145
|
alias Δ_euler_for_free_places Δ_Euler_for_free_places
|
139
146
|
alias ΔE Δ_Euler_for_free_places
|
data/lib/y_petri/transition.rb
CHANGED
@@ -375,25 +375,19 @@ module YPetri
|
|
375
375
|
# rate: λ { |a| a * 0.5 } )
|
376
376
|
#
|
377
377
|
def initialize *args
|
378
|
-
#
|
379
|
-
|
380
|
-
#
|
381
|
-
|
382
|
-
inform_downstream_places
|
383
|
-
@cocked = false # transitions initialize uncocked
|
378
|
+
check_in_arguments *args # the big work of checking in args
|
379
|
+
inform_upstream_places # that they have been connected
|
380
|
+
inform_downstream_places # that they have been connected
|
381
|
+
@cocked = false # transitions initialize uncocked
|
384
382
|
end
|
385
383
|
|
386
384
|
# Marking of the domain places.
|
387
385
|
#
|
388
|
-
def domain_marking
|
389
|
-
domain.map &:marking
|
390
|
-
end
|
386
|
+
def domain_marking; domain.map &:marking end
|
391
387
|
|
392
388
|
# Marking of the codomain places.
|
393
389
|
#
|
394
|
-
def codomain_marking
|
395
|
-
codomain.map &:marking
|
396
|
-
end
|
390
|
+
def codomain_marking; codomain.map &:marking end
|
397
391
|
|
398
392
|
# Result of the transition's "function", regardless of the #enabled? status.
|
399
393
|
#
|
@@ -588,24 +582,15 @@ module YPetri
|
|
588
582
|
#
|
589
583
|
def check_in_arguments *args
|
590
584
|
oo = args.extract_options!
|
591
|
-
oo.may_have :stoichiometry, syn!: [ :stoichio,
|
592
|
-
|
593
|
-
oo.may_have :codomain, syn!: [ :codomain_arcs,
|
594
|
-
:codomain_places,
|
585
|
+
oo.may_have :stoichiometry, syn!: [ :stoichio, :s ]
|
586
|
+
oo.may_have :codomain, syn!: [ :codomain_arcs, :codomain_places,
|
595
587
|
:downstream,
|
596
|
-
:downstream_arcs,
|
597
|
-
:downstream_places,
|
588
|
+
:downstream_arcs, :downstream_places,
|
598
589
|
:action_arcs ]
|
599
|
-
oo.may_have :domain, syn!: [ :domain_arcs,
|
600
|
-
:
|
601
|
-
|
602
|
-
|
603
|
-
:upstream_places ]
|
604
|
-
oo.may_have :rate, syn!: [ :flux,
|
605
|
-
:propensity,
|
606
|
-
:rate_closure,
|
607
|
-
:flux_closure,
|
608
|
-
:propensity_closure ]
|
590
|
+
oo.may_have :domain, syn!: [ :domain_arcs, :domain_places,
|
591
|
+
:upstream, :upstream_arcs, :upstream_places ]
|
592
|
+
oo.may_have :rate, syn!: [ :rate_closure,
|
593
|
+
:propensity, :propensity_closure ]
|
609
594
|
oo.may_have :action, syn!: :action_closure
|
610
595
|
oo.may_have :timed
|
611
596
|
|
data/lib/y_petri/version.rb
CHANGED
@@ -0,0 +1,88 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
|
3
|
+
# Workspace instance methods related to Petri net itsef (places, transitions,
|
4
|
+
# net instances).
|
5
|
+
#
|
6
|
+
module YPetri::Workspace::PetriNetRelatedMethods
|
7
|
+
# Readers for @Place, @Transition, @Net instance variables, which should
|
8
|
+
# contain said classes, or their instance-specific subclasses.
|
9
|
+
|
10
|
+
# Parametrized Place class.
|
11
|
+
#
|
12
|
+
attr_reader :Place
|
13
|
+
|
14
|
+
# Parametrized Transition class.
|
15
|
+
#
|
16
|
+
attr_reader :Transition
|
17
|
+
|
18
|
+
# Parametrized Net class.
|
19
|
+
#
|
20
|
+
attr_reader :Net
|
21
|
+
|
22
|
+
# Instance initialization.
|
23
|
+
#
|
24
|
+
def initialize
|
25
|
+
set_up_Top_net # Sets up :Top net encompassing all places and transitions.
|
26
|
+
super
|
27
|
+
end
|
28
|
+
|
29
|
+
# Returns a place instance identified by the argument.
|
30
|
+
#
|
31
|
+
def place which; Place().instance which end
|
32
|
+
|
33
|
+
# Returns a transition instance identified by the argument.
|
34
|
+
#
|
35
|
+
def transition which; Transition().instance which end
|
36
|
+
|
37
|
+
# Returns a net instance identified by the argument.
|
38
|
+
#
|
39
|
+
def net which; Net().instance which end
|
40
|
+
|
41
|
+
# Returns the name of a place identified by the argument.
|
42
|
+
#
|
43
|
+
def pl which; place( which ).name end
|
44
|
+
|
45
|
+
# Returns the name of a transition identified by the argument.
|
46
|
+
#
|
47
|
+
def tr which; transition( which ).name end
|
48
|
+
|
49
|
+
# Returns the name of a net identified by the argument.
|
50
|
+
#
|
51
|
+
def ne which; net( which ).name end
|
52
|
+
|
53
|
+
# Place instances.
|
54
|
+
#
|
55
|
+
def places; Place().instances end
|
56
|
+
|
57
|
+
# Transition instances.
|
58
|
+
#
|
59
|
+
def transitions; Transition().instances end
|
60
|
+
|
61
|
+
# Net instances.
|
62
|
+
#
|
63
|
+
def nets; Net().instances end
|
64
|
+
|
65
|
+
# Place names.
|
66
|
+
#
|
67
|
+
def pp; places.map &:name end
|
68
|
+
|
69
|
+
# Transition names.
|
70
|
+
#
|
71
|
+
def tt; transitions.map &:name end
|
72
|
+
|
73
|
+
# Net names.
|
74
|
+
#
|
75
|
+
def nn; nets.map &:name end
|
76
|
+
|
77
|
+
private
|
78
|
+
|
79
|
+
# Creates all-encompassing Net instance named :Top.
|
80
|
+
#
|
81
|
+
def set_up_Top_net
|
82
|
+
Net().new name: :Top # all-encompassing :Top net
|
83
|
+
# Hook new places to add themselves magically to the :Top net.
|
84
|
+
Place().new_instance_closure { |new_inst| net( :Top ) << new_inst }
|
85
|
+
# Hook new transitions to add themselves magically to the :Top net.
|
86
|
+
Transition().new_instance_closure { |new_inst| net( :Top ) << new_inst }
|
87
|
+
end
|
88
|
+
end # module YPetri::Workspace::PetriNetRelatedMethods
|
@@ -1,21 +1,9 @@
|
|
1
1
|
# -*- coding: utf-8 -*-
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
# Place class or parametrized subclass.
|
8
|
-
#
|
9
|
-
attr_reader :Place
|
10
|
-
|
11
|
-
# Transition class or parametrized subclass.
|
12
|
-
#
|
13
|
-
attr_reader :Transition
|
14
|
-
|
15
|
-
# Net class or parametrized subclass.
|
16
|
-
#
|
17
|
-
attr_reader :Net
|
18
|
-
|
2
|
+
# Workspace instance methods related to simulation (initial marking
|
3
|
+
# collections, clamp collections, inital marking collections, management
|
4
|
+
# of simulations...)
|
5
|
+
#
|
6
|
+
module YPetri::Workspace::SimulationRelatedMethods
|
19
7
|
# Collections of clamps, initial marking vectors, and simulation settings.
|
20
8
|
#
|
21
9
|
attr_reader :clamp_collections,
|
@@ -25,67 +13,18 @@ module YPetri::Workspace::InstanceMethods
|
|
25
13
|
# Instance initialization.
|
26
14
|
#
|
27
15
|
def initialize
|
28
|
-
set_up_Top_net # Sets up :Top net encompassing all places and transitions.
|
29
|
-
|
30
16
|
@simulations = {} # { simulation => its settings }
|
31
17
|
@clamp_collections = { Base: {} } # { collection name => clamp hash }
|
32
18
|
@initial_marking_collections = { Base: {} } # { collection name => im hash }
|
33
19
|
@simulation_settings_collections = # { collection name => ss hash }
|
34
20
|
{ Base: YPetri::DEFAULT_SIMULATION_SETTINGS.call }
|
21
|
+
super
|
35
22
|
end
|
36
23
|
|
37
|
-
# Returns a place instance identified by the argument.
|
38
|
-
#
|
39
|
-
def place which; Place().instance which end
|
40
|
-
|
41
|
-
# Returns a transition instance identified by the argument.
|
42
|
-
#
|
43
|
-
def transition which; Transition().instance which end
|
44
|
-
|
45
|
-
# Returns a net instance identified by the argument.
|
46
|
-
#
|
47
|
-
def net which; Net().instance which end
|
48
|
-
|
49
|
-
# Returns the name of a place identified by the argument.
|
50
|
-
#
|
51
|
-
def p which; place( which ).name end
|
52
|
-
|
53
|
-
# Returns the name of a transition identified by the argument.
|
54
|
-
#
|
55
|
-
def t which; transition( which ).name end
|
56
|
-
|
57
|
-
# Returns the name of a net identified by the argument.
|
58
|
-
#
|
59
|
-
def n which; net( which ).name end
|
60
|
-
|
61
|
-
# Place instances.
|
62
|
-
#
|
63
|
-
def places; Place().instances end
|
64
|
-
|
65
|
-
# Transition instances.
|
66
|
-
#
|
67
|
-
def transitions; Transition().instances end
|
68
|
-
|
69
|
-
# Net instances.
|
70
|
-
#
|
71
|
-
def nets; Net().instances end
|
72
|
-
|
73
24
|
# Hash of simulation instances and their settings.
|
74
25
|
#
|
75
26
|
def simulations; @simulations end
|
76
27
|
|
77
|
-
# Place names.
|
78
|
-
#
|
79
|
-
def pp; places.map &:name end
|
80
|
-
|
81
|
-
# Transition names.
|
82
|
-
#
|
83
|
-
def tt; transitions.map &:name end
|
84
|
-
|
85
|
-
# Net names.
|
86
|
-
#
|
87
|
-
def nn; nets.map &:name end
|
88
|
-
|
89
28
|
# Clamp collection names.
|
90
29
|
#
|
91
30
|
def clamp_collection_names; @clamp_collections.keys end
|
@@ -239,16 +178,4 @@ module YPetri::Workspace::InstanceMethods
|
|
239
178
|
.merge( initial_marking: im_hash,
|
240
179
|
place_clamps: clamp_hash ) )
|
241
180
|
end # def new_timed_simulation
|
242
|
-
|
243
|
-
private
|
244
|
-
|
245
|
-
# Creates all-encompassing Net instance named :Top.
|
246
|
-
#
|
247
|
-
def set_up_Top_net
|
248
|
-
Net().new name: :Top # all-encompassing :Top net
|
249
|
-
# Hook new places to add themselves magically to the :Top net.
|
250
|
-
Place().new_instance_closure { |new_inst| net( :Top ) << new_inst }
|
251
|
-
# Hook new transitions to add themselves magically to the :Top net.
|
252
|
-
Transition().new_instance_closure { |new_inst| net( :Top ) << new_inst }
|
253
|
-
end
|
254
|
-
end # module YPetri::Workspace::InstanceMethods
|
181
|
+
end # module YPetri::Workspace::SimulationRelatedMethods
|
data/lib/y_petri/workspace.rb
CHANGED
@@ -1,16 +1,16 @@
|
|
1
|
-
#
|
2
|
-
|
3
|
-
#
|
4
|
-
#
|
5
|
-
# provides basic methods for their handling, but these are not too public.
|
6
|
-
# YPetri interface is defined by YPetri::Manipulator.
|
1
|
+
# Workspace holds places, transitions, nets and other assets needed to set up
|
2
|
+
# and simulate Petri nets (settings, clamps, initial markings etc.). Workspace
|
3
|
+
# provides basic, decent, vanilla methods to just do what is necessary. It is
|
4
|
+
# up to YPetri::Manipulator to provide ergonomical DSL to the user.
|
7
5
|
#
|
8
6
|
class YPetri::Workspace
|
9
7
|
include NameMagic
|
10
8
|
|
11
|
-
require_relative 'workspace/
|
9
|
+
require_relative 'workspace/petri_net_related_methods'
|
12
10
|
require_relative 'workspace/parametrized_subclassing'
|
11
|
+
require_relative 'workspace/simulation_related_methods'
|
13
12
|
|
14
|
-
include self::
|
13
|
+
include self::PetriNetRelatedMethods
|
15
14
|
prepend self::ParametrizedSubclassing
|
15
|
+
include self::SimulationRelatedMethods
|
16
16
|
end
|