1 // Copyright (c) 1994 James Clark
2 // See the file COPYING for copying permission.
3 #pragma ident "%Z%%M% %I% %E% SMI"
5 #ifndef RangeMap_DEF_INCLUDED
6 #define RangeMap_DEF_INCLUDED 1
13 namespace SP_NAMESPACE
{
16 template<class From
, class To
>
17 RangeMap
<From
, To
>::RangeMap()
21 template<class From
, class To
>
22 Boolean RangeMap
<From
, To
>::map(From from
, To
&to
, From
&alsoMax
) const
24 // FIXME use binary search
25 for (size_t i
= 0; i
< ranges_
.size(); i
++) {
26 const RangeMapRange
<From
,To
> &r
= ranges_
[i
];
27 if (r
.fromMin
<= from
&& from
<= r
.fromMax
) {
28 to
= r
.toMin
+ (from
- r
.fromMin
);
32 if (r
.fromMin
> from
) {
33 alsoMax
= r
.fromMin
- 1;
42 typedef ISet
<WideChar
> RangeMap_dummy
;
44 template<class From
, class To
>
45 unsigned RangeMap
<From
, To
>::inverseMap(To to
, From
&from
,
46 ISet
<WideChar
> &fromSet
,
47 WideChar
&count
) const
49 // FIXME use binary search
52 for (size_t i
= 0; i
< ranges_
.size(); i
++) {
53 const RangeMapRange
<From
,To
> &r
= ranges_
[i
];
54 if (r
.toMin
<= to
&& to
<= r
.toMin
+ (r
.fromMax
- r
.fromMin
)) {
55 From n
= r
.fromMin
+ (to
- r
.toMin
);
56 WideChar thisCount
= r
.fromMax
- n
+ 1;
59 if (thisCount
< count
)
66 if (thisCount
< count
)
75 else if (ret
== 0 && r
.toMin
> to
&& (r
.toMin
- to
< count
))
81 template<class From
, class To
>
82 RangeMapIter
<From
, To
>::RangeMapIter(const RangeMap
<From
, To
> &map
)
83 : count_(map
.ranges_
.size()), ptr_(map
.ranges_
.begin())
87 // If the new range overlaps an existing one, the new
88 // one takes precedence.
90 template<class From
, class To
>
91 void RangeMap
<From
, To
>::addRange(From fromMin
, From fromMax
, To toMin
)
93 // FIXME use binary search
95 for (i
= ranges_
.size(); i
> 0; i
--)
96 if (fromMin
> ranges_
[i
- 1].fromMax
)
98 // fromMin <= ranges[i].fromMax
99 Boolean coalesced
= 0;
101 && ranges_
[i
- 1].fromMax
+ 1 == fromMin
102 && ranges_
[i
- 1].toMin
+ (fromMin
- ranges_
[i
- 1].fromMin
) == toMin
) {
103 // coalesce with previous
104 ranges_
[i
- 1].fromMax
= fromMax
;
108 else if (i
< ranges_
.size() && fromMax
>= ranges_
[i
].fromMin
- 1) {
110 if (fromMin
<= ranges_
[i
].fromMin
) {
111 if (toMin
+ (ranges_
[i
].fromMin
- fromMin
) == ranges_
[i
].toMin
) {
112 ranges_
[i
].fromMin
= fromMin
;
113 if (fromMax
<= ranges_
[i
].fromMax
)
115 ranges_
[i
].fromMax
= fromMax
;
120 // fromMin > ranges_[i].fromMin
121 if (ranges_
[i
].toMin
+ (fromMin
- ranges_
[i
].fromMin
) == toMin
) {
122 if (fromMax
< ranges_
[i
].fromMax
)
124 ranges_
[i
].fromMax
= fromMax
;
131 ranges_
.resize(ranges_
.size() + 1);
132 for (size_t j
= ranges_
.size() - 1; j
> i
; j
--)
133 ranges_
[j
] = ranges_
[j
- 1];
134 ranges_
[i
].fromMin
= fromMin
;
135 ranges_
[i
].fromMax
= fromMax
;
136 ranges_
[i
].toMin
= toMin
;
138 // Delete overlapping ranges starting at i + 1.
140 for (j
= i
+ 1; j
< ranges_
.size(); j
++) {
141 if (fromMax
< ranges_
[j
].fromMax
) {
142 if (fromMax
>= ranges_
[j
].fromMin
)
143 ranges_
[j
].fromMin
= fromMax
+ 1;
148 // delete i + 1 ... j - 1
151 size_t count
= ranges_
.size() - j
;
152 for (size_t k
= 0; k
< count
; k
++)
153 ranges_
[i
+ 1 + count
] = ranges_
[j
+ count
];
154 ranges_
.resize(ranges_
.size() - (j
- (i
+ 1)));
162 #endif /* not RangeMap_DEF_INCLUDED */