@@ -133,7 +133,10 @@ function split_system(ci::ClockInference{S}) where {S}
133133 tss = similar (cid_to_eq, S)
134134 for (id, ieqs) in enumerate (cid_to_eq)
135135 ts_i = system_subset (ts, ieqs)
136- @set! ts_i. structure. only_discrete = id != continuous_id
136+ if id != continuous_id
137+ ts_i = shift_discrete_system (ts_i)
138+ @set! ts_i. structure. only_discrete = true
139+ end
137140 tss[id] = ts_i
138141 end
139142 return tss, inputs, continuous_id, id_to_clock
@@ -148,7 +151,7 @@ function generate_discrete_affect(
148151 end
149152 use_index_cache = has_index_cache (osys) && get_index_cache (osys) != = nothing
150153 out = Sym {Any} (:out )
151- appended_parameters = parameters (syss[continuous_id])
154+ appended_parameters = full_parameters (syss[continuous_id])
152155 offset = length (appended_parameters)
153156 param_to_idx = if use_index_cache
154157 Dict {Any, ParameterIndex} (p => parameter_index (osys, p)
@@ -180,40 +183,46 @@ function generate_discrete_affect(
180183 disc_to_cont_idxs = Int[]
181184 end
182185 for v in inputs[continuous_id]
183- vv = arguments (v)[1 ]
184- if vv in fullvars
185- push! (needed_disc_to_cont_obs, vv)
186+ _v = arguments (v)[1 ]
187+ if _v in fullvars
188+ push! (needed_disc_to_cont_obs, _v)
189+ push! (disc_to_cont_idxs, param_to_idx[v])
190+ continue
191+ end
192+
193+ # If the held quantity is calculated through observed
194+ # it will be shifted forward by 1
195+ _v = Shift (get_iv (sys), 1 )(_v)
196+ if _v in fullvars
197+ push! (needed_disc_to_cont_obs, _v)
186198 push! (disc_to_cont_idxs, param_to_idx[v])
199+ continue
187200 end
188201 end
189- append! (appended_parameters, input, unknowns (sys) )
202+ append! (appended_parameters, input)
190203 cont_to_disc_obs = build_explicit_observed_function (
191204 use_index_cache ? osys : syss[continuous_id],
192205 needed_cont_to_disc_obs,
193206 throw = false ,
194207 expression = true ,
195208 output_type = SVector)
196- @set! sys. ps = appended_parameters
197209 disc_to_cont_obs = build_explicit_observed_function (sys, needed_disc_to_cont_obs,
198210 throw = false ,
199211 expression = true ,
200212 output_type = SVector,
201- ps = reorder_parameters (osys, full_parameters (sys)))
213+ op = Shift,
214+ ps = reorder_parameters (osys, appended_parameters))
202215 ni = length (input)
203216 ns = length (unknowns (sys))
204217 disc = Func (
205218 [
206219 out,
207220 DestructuredArgs (unknowns (osys)),
208- if use_index_cache
209- DestructuredArgs .(reorder_parameters (osys, full_parameters (osys)))
210- else
211- (DestructuredArgs (appended_parameters),)
212- end ... ,
221+ DestructuredArgs .(reorder_parameters (osys, full_parameters (osys)))... ,
213222 get_iv (sys)
214223 ],
215224 [],
216- let_block)
225+ let_block) |> toexpr
217226 if use_index_cache
218227 cont_to_disc_idxs = [parameter_index (osys, sym) for sym in input]
219228 disc_range = [parameter_index (osys, sym) for sym in unknowns (sys)]
@@ -235,8 +244,14 @@ function generate_discrete_affect(
235244 end
236245 empty_disc = isempty (disc_range)
237246 disc_init = if use_index_cache
238- :(function (p, t)
247+ :(function (u, p, t)
248+ c2d_obs = $ cont_to_disc_obs
239249 d2c_obs = $ disc_to_cont_obs
250+ result = c2d_obs (u, p... , t)
251+ for (val, i) in zip (result, $ cont_to_disc_idxs)
252+ $ (_set_parameter_unchecked!)(p, val, i; update_dependent = false )
253+ end
254+
240255 disc_state = Tuple ($ (parameter_values)(p, i) for i in $ disc_range)
241256 result = d2c_obs (disc_state, p... , t)
242257 for (val, i) in zip (result, $ disc_to_cont_idxs)
@@ -248,11 +263,14 @@ function generate_discrete_affect(
248263 repack (discretes) # to force recalculation of dependents
249264 end )
250265 else
251- :(function (p, t)
266+ :(function (u, p, t)
267+ c2d_obs = $ cont_to_disc_obs
252268 d2c_obs = $ disc_to_cont_obs
269+ c2d_view = view (p, $ cont_to_disc_idxs)
253270 d2c_view = view (p, $ disc_to_cont_idxs)
254- disc_state = view (p, $ disc_range)
255- copyto! (d2c_view, d2c_obs (disc_state, p, t))
271+ disc_unknowns = view (p, $ disc_range)
272+ copyto! (c2d_view, c2d_obs (u, p, t))
273+ copyto! (d2c_view, d2c_obs (disc_unknowns, p, t))
256274 end )
257275 end
258276
@@ -277,9 +295,6 @@ function generate_discrete_affect(
277295 # TODO : find a way to do this without allocating
278296 disc = $ disc
279297
280- push! (saved_values. t, t)
281- push! (saved_values. saveval, $ save_vec)
282-
283298 # Write continuous into to discrete: handles `Sample`
284299 # Write discrete into to continuous
285300 # Update discrete unknowns
@@ -329,6 +344,10 @@ function generate_discrete_affect(
329344 :(copyto! (d2c_view, d2c_obs (disc_unknowns, p, t)))
330345 end
331346 )
347+
348+ push! (saved_values. t, t)
349+ push! (saved_values. saveval, $ save_vec)
350+
332351 # @show "after d2c", p
333352 $ (
334353 if use_index_cache
0 commit comments