8b1160ff6d93c44b73dd23004f790d17033aa07b
[oweals/cde.git] / cde / programs / nsgmls / SubstTable.C
1 /* $XConsortium: SubstTable.C /main/1 1996/07/29 17:05:48 cde-hp $ */
2 // Copyright (c) 1994 James Clark
3 // See the file COPYING for copying permission.
4
5 #ifndef SubstTable_DEF_INCLUDED
6 #define SubstTable_DEF_INCLUDED 1
7
8 #ifdef SP_NAMESPACE
9 namespace SP_NAMESPACE {
10 #endif
11
12 template<class T>
13 SubstTable<T>::SubstTable()
14 : pairsValid_(1)
15 {
16 }
17
18 template<class T>
19 void SubstTable<T>::addSubst(T from, T to)
20 {
21   if (table_.size() == 0) {
22     table_.resize(T(-1) + 1);
23     for (int i = 0; i < T(-1) + 1; i++)
24       table_[i] = i;
25   }
26   if (table_[from] != to)
27     pairsValid_ = 0;
28   table_[from] = to;
29 }
30
31 template<class T>
32 String<T> SubstTable<T>::inverse(T ch) const
33 {
34   if (!pairsValid_) {
35     const T *p = table_.data();
36     size_t length = table_.size();
37     for (size_t i = 0; i < length; i++)
38       if (p[i] != i) {
39         // FIXME use mutable if available
40         ((SubstTable<T> *)this)->pairs_ += T(i);
41         ((SubstTable<T> *)this)->pairs_ += p[i];
42       }
43     ((SubstTable<T> *)this)->pairsValid_ = 1;
44   }
45   const T *p = pairs_.data();
46   if (!p)
47     return String<T>(&ch, 1);
48   String<T> result;
49   if (table_[ch] == ch)
50     result += ch;
51   for (size_t n = pairs_.size(); n > 0; n -= 2, p += 2)
52     if (p[1] == ch)
53       result += p[0];
54   return result;
55 }
56
57 template<class T>
58 void SubstTable<T>::inverseTable(SubstTable<T> &inv) const
59 {
60   if (table_.size() == 0) {
61     inv.table_.resize(0);
62     inv.pairs_.resize(0);
63     inv.pairsValid_ = 1;
64   }
65   else {
66     if (inv.table_.size() == 0)
67       inv.table_.resize(T(-1) + 1);
68     int i;
69     for (i = 0; i < T(-1) + 1; i++)
70       inv.table_[i] = i;
71     inv.pairs_.resize(0);
72     inv.pairsValid_ = 0;
73     for (i = 0; i < T(-1) + 1; i++)
74       if (table_[i] != i)
75         inv.table_[table_[i]] = i;
76   }
77 }
78
79 template<class T>
80 void SubstTable<T>::subst(String<T> &str) const
81 {
82   for (size_t i = 0; i < str.size(); i++)
83     subst(str[i]);
84 }
85
86 #ifdef SP_NAMESPACE
87 }
88 #endif
89
90 #endif /* not SubstTable_DEF_INCLUDED */