@@ -52,7 +52,7 @@ local string, table, io =
52
52
53
53
-- backup original methods and metamethods
54
54
local sequence_mt = getmetatable(sequence)
55
- local var_get, var_val, raw_get, is_instanceOf in sequence
55
+ local var_get, var_val, is_instanceOf in sequence
56
56
local seq_cpy, var_set = sequence.copy, sequence_mt.__newindex
57
57
58
58
-- root object ----------------------------------------------------------------o
133
133
-- check shared element
134
134
local function check_shared (seq, idx)
135
135
local elm = seq.__dat[idx]
136
- if is_nil(raw_get( elm, 'l') ) then return elm.parent end
136
+ if is_nil(elm:raw_get 'l') then return elm.parent end
137
137
seq_error("invalid shared element (l defined)", seq, idx, elm)
138
138
end
139
139
644
644
local function flatten_sequ (seq, flat, sref)
645
645
local n, idx = seq:raw_len(), 2
646
646
flat[1] = mkstart {at=0}
647
+
647
648
for i=1,n do
648
- local elm = seq:raw_get (i)
649
+ local elm = seq:var_get (i)
649
650
if not (is_element(elm) or is_rawtable(elm)) then
650
651
seq_error("invalid element detected", seq, i)
651
652
elseif elm.kind == 'bline' or is_rawtable(elm) then
@@ -706,7 +707,7 @@ local function clear_sub (seq, sref)
706
707
end
707
708
708
709
-- finalize sequence
709
- local function finish_sequ (seq)
710
+ local function fini_sequ (seq)
710
711
local data = seq.__dat
711
712
712
713
-- clear memoization
@@ -729,31 +730,33 @@ end
729
730
-- sequence init (build)
730
731
local function init_mm (seq)
731
732
local n = seq:raw_len()
733
+
734
+ -- check if sequence needs __dat
735
+ if n == 0 and is_nil(seq:raw_get'l') then return seq end
736
+
732
737
local sref = { dir=seq.dir, sdir={} }
733
738
local data = table.new(n+2,8)
734
739
735
- -- disable inheritance
736
- -- seq:set_final()
737
-
738
740
-- flatten subsequences
739
741
flatten_sequ(seq, data, sref)
740
742
seq:clear_array()
741
743
742
- local ne = #data
744
+ local ne = #data
743
745
data.eidx = table.new(0,ne)
744
746
data.spos = table.new(ne,0)
745
747
data.upos = table.new(ne,0)
746
748
data.ds = table.new(ne,0)
747
749
data.algn = table.new(ne,0)
748
- seq.__dat, data.ne = data, ne
750
+ data.ne = ne
751
+ seq.__dat = data
749
752
750
753
-- set minlen to 1e-6 [m] for MAD-X compatibility
751
754
if option.madxenv then seq.minlen = 1e-6 end
752
755
753
756
build_idx(data)
754
757
build_pos(seq, sref)
755
758
clear_sub(seq, sref)
756
- finish_sequ (seq)
759
+ fini_sequ (seq)
757
760
758
761
-- publish sequence elements in MADX environment
759
762
if option.madxenv then seq:publish(MADX, true) end
@@ -764,27 +767,30 @@ end
764
767
local function copy_mm (seq, name_)
765
768
assert(not rawequal(seq, sequence), "invalid argument #1 (cannot copy 'sequence')")
766
769
assert(is_sequence(seq) , "invalid argument #1 (sequence expected)")
767
- local cpy = seq_cpy(seq,name_)
770
+ local cpy = seq_cpy(seq,name_)
771
+
772
+ -- check if copy needs to be further processed
773
+ if seq:is_view() then return cpy end
774
+
768
775
local data = seq.__dat
769
776
local ne = data.ne
770
- local cdat = table.new(ne,5 ) -- see init_mm
777
+ local cdat = table.new(ne,8 ) -- see init_mm
771
778
cdat.eidx = table.new(0,ne)
772
779
cdat.spos = table.new(ne,0)
773
780
cdat.upos = table.new(ne,0)
774
781
cdat.ds = table.new(ne,0)
775
782
cdat.algn = table.new(ne,0)
776
783
cdat.ne = ne
784
+ cpy.__dat = cdat
777
785
778
786
for i=1,ne do
779
787
cdat[i] = data[i]:copy()
780
788
cdat.spos[i], cdat.upos[i], cdat.ds[i], cdat.algn[i] =
781
789
data.spos[i], data.upos[i], data.ds[i], data.algn[i]
782
790
end
783
791
784
- cpy:raw_set('__dat', cdat)
785
-
786
792
build_idx(cdat)
787
- finish_sequ (cpy)
793
+ fini_sequ (cpy)
788
794
return cpy
789
795
end
790
796
842
848
843
849
-- methods (readonly) ---------------------------------------------------------o
844
850
851
+ local function is_view (seq)
852
+ assert(is_sequence(seq), "invalid argument #1 (sequence expected)")
853
+ return is_nil(seq:raw_get'__dat')
854
+ end
855
+
845
856
local function index (seq, idx)
846
857
assert(is_sequence(seq), "invalid argument #1 (sequence expected)")
847
858
assert(is_integer (idx), "invalid argument #2 (integer expected)")
@@ -1121,7 +1132,7 @@ local function build_index (seq)
1121
1132
assert(is_sequence(seq), "invalid argument #1 (sequence expected)")
1122
1133
local data = seq.__dat
1123
1134
build_idx (data)
1124
- finish_sequ (seq)
1135
+ fini_sequ (seq)
1125
1136
return seq
1126
1137
end
1127
1138
@@ -1416,7 +1427,7 @@ local function share (seq1, seq2)
1416
1427
end
1417
1428
end
1418
1429
end
1419
- finish_sequ (seq1) finish_sequ (seq2)
1430
+ fini_sequ (seq1) fini_sequ (seq2)
1420
1431
return elm_r, idx_r
1421
1432
end
1422
1433
@@ -1453,7 +1464,7 @@ local function unique (seq, fmt_)
1453
1464
if fmt_ then data.eidx[en] = nil end
1454
1465
end
1455
1466
end
1456
- finish_sequ (seq)
1467
+ fini_sequ (seq)
1457
1468
return seq
1458
1469
end
1459
1470
@@ -1724,6 +1735,9 @@ sequence :set_methods {
1724
1735
-- duplicate
1725
1736
copy = copy_mm,
1726
1737
1738
+ -- ownership
1739
+ is_view = is_view,
1740
+
1727
1741
-- flags
1728
1742
save_flags = save_flags,
1729
1743
restore_flags = restore_flags,
0 commit comments