@@ -19,37 +19,51 @@ pub struct TzifBlockV2 {
1919 pub transition_times : Vec < i64 > ,
2020 pub transition_types : Vec < u8 > ,
2121 pub local_time_types : Vec < LocalTimeRecord > , // TODO: Add other fields as needed
22+ pub designations : Vec < char > ,
2223}
2324
2425impl TzifBlockV2 {
2526 pub fn from_transition_data ( data : & CompiledTransitions ) -> Self {
2627 let mut local_time_set = IndexSet :: new ( ) ;
28+ let mut designation_set = DesignationSet :: default ( ) ;
29+
30+ let index = designation_set
31+ . insert_and_retrieve_index ( data. initial_record . designation . chars ( ) . collect ( ) ) ;
2732 local_time_set. insert ( LocalTimeRecord {
2833 offset : data. initial_record . offset ,
2934 is_dst : data. initial_record . saving . as_secs ( ) != 0 ,
35+ index : index as u8 ,
3036 } ) ;
3137 let mut transition_times = Vec :: default ( ) ;
3238 let mut transition_types = Vec :: default ( ) ;
3339 for transition in & data. transitions {
34- let _ = local_time_set. insert ( LocalTimeRecord {
40+ let index =
41+ designation_set. insert_and_retrieve_index ( transition. format . chars ( ) . collect ( ) ) ;
42+ let local_time_record = LocalTimeRecord {
3543 offset : transition. offset ,
3644 is_dst : transition. dst ,
37- } ) ;
45+ index : index as u8 ,
46+ } ;
3847
3948 transition_times. push ( transition. at_time ) ;
40- for ( index, time_type) in local_time_set. iter ( ) . enumerate ( ) {
41- if time_type. offset == transition. offset {
42- transition_types. push ( index as u8 ) ;
49+ match local_time_set. get_index_of ( & local_time_record) {
50+ Some ( i) => transition_types. push ( i as u8 ) ,
51+ None => {
52+ let _ = local_time_set. insert ( local_time_record) ;
53+ transition_types. push ( local_time_set. len ( ) as u8 - 1 ) ;
4354 }
4455 }
4556 }
4657
4758 let local_time_types = local_time_set. into_iter ( ) . collect :: < Vec < LocalTimeRecord > > ( ) ;
4859
60+ let designations = designation_set. to_vec ( ) ;
61+
4962 Self {
5063 transition_times,
5164 transition_types,
5265 local_time_types,
66+ designations,
5367 }
5468 }
5569}
@@ -59,4 +73,44 @@ impl TzifBlockV2 {
5973pub struct LocalTimeRecord {
6074 pub offset : i64 ,
6175 pub is_dst : bool ,
76+ pub index : u8 ,
77+ }
78+
79+ #[ derive( Debug , Default , Clone ) ]
80+ pub struct DesignationSet {
81+ pub designations : IndexSet < Vec < char > > ,
82+ pub indices : Vec < usize > ,
83+ pub next_index : usize ,
84+ }
85+
86+ impl DesignationSet {
87+ // Inserts the a designation if it doesn't exist, returns the designation index.
88+ pub fn insert_and_retrieve_index ( & mut self , mut designation : Vec < char > ) -> usize {
89+ // Add a null character
90+ designation. push ( '\0' ) ;
91+ // Check if the designation already exists.
92+ let Some ( index) = self . designations . get_index_of ( & designation) else {
93+ let designation_len = designation. len ( ) ;
94+
95+ // Insert the new designation into the set
96+ let _ = self . designations . insert ( designation) ;
97+
98+ // Get the designation index and cache it.
99+ let designation_index = self . next_index ;
100+ self . indices . push ( designation_index) ;
101+
102+ // Calculate the next index to give out.
103+ self . next_index += designation_len;
104+
105+ return designation_index;
106+ } ;
107+ self . indices [ index]
108+ }
109+
110+ pub fn to_vec ( self ) -> Vec < char > {
111+ self . designations
112+ . into_iter ( )
113+ . collect :: < Vec < Vec < char > > > ( )
114+ . concat ( )
115+ }
62116}
0 commit comments