OLD | NEW |
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 part of fixnum; | 5 part of fixnum; |
6 | 6 |
7 /** | 7 /** |
8 * An immutable 32-bit signed integer, in the range [-2^31, 2^31 - 1]. | 8 * An immutable 32-bit signed integer, in the range [-2^31, 2^31 - 1]. |
9 * Arithmetic operations may overflow in order to maintain this range. | 9 * Arithmetic operations may overflow in order to maintain this range. |
10 */ | 10 */ |
(...skipping 120 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
131 final int _i; | 131 final int _i; |
132 | 132 |
133 const int32._internal(int i) : _i = i; | 133 const int32._internal(int i) : _i = i; |
134 | 134 |
135 /** | 135 /** |
136 * Constructs an [int32] from an [int]. Only the low 32 bits of the input | 136 * Constructs an [int32] from an [int]. Only the low 32 bits of the input |
137 * are used. | 137 * are used. |
138 */ | 138 */ |
139 int32.fromInt(int i) : _i = (i & 0x7fffffff) - (i & 0x80000000); | 139 int32.fromInt(int i) : _i = (i & 0x7fffffff) - (i & 0x80000000); |
140 | 140 |
141 // Convert an [int] or [intx] to an [int32]. Note that an [int64] | 141 // Returns the [int] representation of the specified value. Throws |
142 // will be truncated. | 142 // [ArgumentError] for non-integer arguments. |
143 int _convert(other) { | 143 int _toInt(val) { |
144 if (other == null) { | 144 if (val is int32) { |
145 throw new ArgumentError(null); | 145 return val._i; |
146 } else if (other is intx) { | 146 } else if (val is int) { |
147 return other.toInt32()._i; | 147 return val; |
148 } else if (other is int) { | |
149 return other; | |
150 } else { | |
151 throw new Exception("Can't retrieve 32-bit int from $other"); | |
152 } | 148 } |
| 149 throw new ArgumentError(val); |
153 } | 150 } |
154 | 151 |
155 // The +, -, * , &, |, and ^ operaters deal with types as follows: | 152 // The +, -, * , &, |, and ^ operaters deal with types as follows: |
156 // | 153 // |
157 // int32 + int => int32 | 154 // int32 + int => int32 |
158 // int32 + int32 => int32 | 155 // int32 + int32 => int32 |
159 // int32 + int64 => int64 | 156 // int32 + int64 => int64 |
160 // | 157 // |
161 // The %, ~/ and remainder operators return an int32 even with an int64 | 158 // The %, ~/ and remainder operators return an int32 even with an int64 |
162 // argument, since the result cannot be greater than the value on the | 159 // argument, since the result cannot be greater than the value on the |
163 // left-hand side: | 160 // left-hand side: |
164 // | 161 // |
165 // int32 % int => int32 | 162 // int32 % int => int32 |
166 // int32 % int32 => int32 | 163 // int32 % int32 => int32 |
167 // int32 % int64 => int32 | 164 // int32 % int64 => int32 |
168 | 165 |
169 intx operator +(other) { | 166 intx operator +(other) { |
170 if (other is int64) { | 167 if (other is int64) { |
171 return this.toInt64() + other; | 168 return this.toInt64() + other; |
172 } | 169 } |
173 return new int32.fromInt(_i + _convert(other)); | 170 return new int32.fromInt(_i + _toInt(other)); |
174 } | 171 } |
175 | 172 |
176 intx operator -(other) { | 173 intx operator -(other) { |
177 if (other is int64) { | 174 if (other is int64) { |
178 return this.toInt64() - other; | 175 return this.toInt64() - other; |
179 } | 176 } |
180 return new int32.fromInt(_i - _convert(other)); | 177 return new int32.fromInt(_i - _toInt(other)); |
181 } | 178 } |
182 | 179 |
183 int32 operator -() => new int32.fromInt(-_i); | 180 int32 operator -() => new int32.fromInt(-_i); |
184 | 181 |
185 intx operator *(other) { | 182 intx operator *(other) { |
186 if (other is int64) { | 183 if (other is int64) { |
187 return this.toInt64() * other; | 184 return this.toInt64() * other; |
188 } | 185 } |
189 // TODO(rice) - optimize | 186 // TODO(rice) - optimize |
190 return (this.toInt64() * other).toInt32(); | 187 return (this.toInt64() * other).toInt32(); |
191 } | 188 } |
192 | 189 |
193 int32 operator %(other) { | 190 int32 operator %(other) { |
194 if (other is int64) { | 191 if (other is int64) { |
195 // Result will be int32 | 192 // Result will be int32 |
196 return (this.toInt64() % other).toInt32(); | 193 return (this.toInt64() % other).toInt32(); |
197 } | 194 } |
198 return new int32.fromInt(_i % _convert(other)); | 195 return new int32.fromInt(_i % _toInt(other)); |
199 } | 196 } |
200 | 197 |
201 int32 operator ~/(other) { | 198 int32 operator ~/(other) { |
202 if (other is int64) { | 199 if (other is int64) { |
203 // Result will be int32 | |
204 return (this.toInt64() ~/ other).toInt32(); | 200 return (this.toInt64() ~/ other).toInt32(); |
205 } | 201 } |
206 return new int32.fromInt(_i ~/ _convert(other)); | 202 return new int32.fromInt(_i ~/ _toInt(other)); |
207 } | 203 } |
208 | 204 |
209 int32 remainder(other) { | 205 int32 remainder(other) { |
210 if (other is int64) { | 206 if (other is int64) { |
211 // Result will be int32 | |
212 int64 t = this.toInt64(); | 207 int64 t = this.toInt64(); |
213 return (t - (t ~/ other) * other).toInt32(); | 208 return (t - (t ~/ other) * other).toInt32(); |
214 } | 209 } |
215 return this - (this ~/ other) * other; | 210 return this - (this ~/ other) * other; |
216 } | 211 } |
217 | 212 |
218 int32 operator &(other) { | 213 int32 operator &(other) { |
219 if (other is int64) { | 214 if (other is int64) { |
220 return (this.toInt64() & other).toInt32(); | 215 return (this.toInt64() & other).toInt32(); |
221 } | 216 } |
222 return new int32.fromInt(_i & _convert(other)); | 217 return new int32.fromInt(_i & _toInt(other)); |
223 } | 218 } |
224 | 219 |
225 int32 operator |(other) { | 220 int32 operator |(other) { |
226 if (other is int64) { | 221 if (other is int64) { |
227 return (this.toInt64() | other).toInt32(); | 222 return (this.toInt64() | other).toInt32(); |
228 } | 223 } |
229 return new int32.fromInt(_i | _convert(other)); | 224 return new int32.fromInt(_i | _toInt(other)); |
230 } | 225 } |
231 | 226 |
232 int32 operator ^(other) { | 227 int32 operator ^(other) { |
233 if (other is int64) { | 228 if (other is int64) { |
234 return (this.toInt64() ^ other).toInt32(); | 229 return (this.toInt64() ^ other).toInt32(); |
235 } | 230 } |
236 return new int32.fromInt(_i ^ _convert(other)); | 231 return new int32.fromInt(_i ^ _toInt(other)); |
237 } | 232 } |
238 | 233 |
239 int32 operator ~() => new int32.fromInt(~_i); | 234 int32 operator ~() => new int32.fromInt(~_i); |
240 | 235 |
241 int32 operator <<(int n) { | 236 int32 operator <<(int n) { |
242 if (n < 0) { | 237 if (n < 0) { |
243 throw new ArgumentError("$n"); | 238 throw new ArgumentError("$n"); |
244 } | 239 } |
245 n &= 31; | 240 n &= 31; |
246 return new int32.fromInt(_i << n); | 241 return new int32.fromInt(_i << n); |
(...skipping 25 matching lines...) Expand all Loading... |
272 value = (_i >> n) & ((1 << (32 - n)) - 1); | 267 value = (_i >> n) & ((1 << (32 - n)) - 1); |
273 } | 268 } |
274 return new int32.fromInt(value); | 269 return new int32.fromInt(value); |
275 } | 270 } |
276 | 271 |
277 /** | 272 /** |
278 * Returns [true] if this [int32] has the same numeric value as the | 273 * Returns [true] if this [int32] has the same numeric value as the |
279 * given object. The argument may be an [int] or an [intx]. | 274 * given object. The argument may be an [int] or an [intx]. |
280 */ | 275 */ |
281 bool operator ==(other) { | 276 bool operator ==(other) { |
282 if (other == null) { | 277 if (other is int32) { |
283 return false; | 278 return _i == other._i; |
| 279 } else if (other is int64) { |
| 280 return this.toInt64() == other; |
| 281 } else if (other is int) { |
| 282 return _i == other; |
284 } | 283 } |
285 if (other is int64) { | 284 return false; |
286 return this.toInt64() == other; | |
287 } | |
288 return _i == _convert(other); | |
289 } | 285 } |
290 | 286 |
291 int compareTo(Comparable other) { | 287 int compareTo(Comparable other) { |
292 if (other is int64) { | 288 if (other is int64) { |
293 return this.toInt64().compareTo(other); | 289 return this.toInt64().compareTo(other); |
294 } | 290 } |
295 return _i.compareTo(_convert(other)); | 291 return _i.compareTo(_toInt(other)); |
296 } | 292 } |
297 | 293 |
298 bool operator <(other) { | 294 bool operator <(other) { |
299 if (other is int64) { | 295 if (other is int64) { |
300 return this.toInt64() < other; | 296 return this.toInt64() < other; |
301 } | 297 } |
302 return _i < _convert(other); | 298 return _i < _toInt(other); |
303 } | 299 } |
304 | 300 |
305 bool operator <=(other) { | 301 bool operator <=(other) { |
306 if (other is int64) { | 302 if (other is int64) { |
307 return this.toInt64() < other; | 303 return this.toInt64() <= other; |
308 } | 304 } |
309 return _i <= _convert(other); | 305 return _i <= _toInt(other); |
310 } | 306 } |
311 | 307 |
312 bool operator >(other) { | 308 bool operator >(other) { |
313 if (other is int64) { | 309 if (other is int64) { |
314 return this.toInt64() < other; | 310 return this.toInt64() > other; |
315 } | 311 } |
316 return _i > _convert(other); | 312 return _i > _toInt(other); |
317 } | 313 } |
318 | 314 |
319 bool operator >=(other) { | 315 bool operator >=(other) { |
320 if (other is int64) { | 316 if (other is int64) { |
321 return this.toInt64() < other; | 317 return this.toInt64() >= other; |
322 } | 318 } |
323 return _i >= _convert(other); | 319 return _i >= _toInt(other); |
324 } | 320 } |
325 | 321 |
326 bool get isEven => (_i & 0x1) == 0; | 322 bool get isEven => (_i & 0x1) == 0; |
327 bool get isMaxValue => _i == 2147483647; | 323 bool get isMaxValue => _i == 2147483647; |
328 bool get isMinValue => _i == -2147483648; | 324 bool get isMinValue => _i == -2147483648; |
329 bool get isNegative => _i < 0; | 325 bool get isNegative => _i < 0; |
330 bool get isOdd => (_i & 0x1) == 1; | 326 bool get isOdd => (_i & 0x1) == 1; |
331 bool get isZero => _i == 0; | 327 bool get isZero => _i == 0; |
332 | 328 |
333 int get hashCode => _i; | 329 int get hashCode => _i; |
(...skipping 13 matching lines...) Expand all Loading... |
347 } | 343 } |
348 | 344 |
349 int toInt() => _i; | 345 int toInt() => _i; |
350 int32 toInt32() => this; | 346 int32 toInt32() => this; |
351 int64 toInt64() => new int64.fromInt(_i); | 347 int64 toInt64() => new int64.fromInt(_i); |
352 | 348 |
353 String toString() => _i.toString(); | 349 String toString() => _i.toString(); |
354 String toHexString() => _i.toRadixString(16); | 350 String toHexString() => _i.toRadixString(16); |
355 String toRadixString(int radix) => _i.toRadixString(radix); | 351 String toRadixString(int radix) => _i.toRadixString(radix); |
356 } | 352 } |
OLD | NEW |