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 library deep_equals; | 5 library deep_equals; |
6 | 6 |
7 /** | 7 /// Returns whether two objects are structurally equivalent. This considers NaN |
8 * Returns whether two objects are structurally equivalent. This considers NaN | 8 /// values to be equivalent. It also handles self-referential structures. |
9 * values to be equivalent. It also handles self-referential structures. | |
10 */ | |
11 bool deepEquals(obj1, obj2, [List parents1, List parents2]) { | 9 bool deepEquals(obj1, obj2, [List parents1, List parents2]) { |
12 if (identical(obj1, obj2)) return true; | 10 if (identical(obj1, obj2)) return true; |
13 if (parents1 == null) { | 11 if (parents1 == null) { |
14 parents1 = []; | 12 parents1 = []; |
15 parents2 = []; | 13 parents2 = []; |
16 } | 14 } |
17 | 15 |
18 // parents1 and parents2 are guaranteed to be the same size. | 16 // parents1 and parents2 are guaranteed to be the same size. |
19 for (var i = 0; i < parents1.length; i++) { | 17 for (var i = 0; i < parents1.length; i++) { |
20 var loop1 = identical(obj1, parents1[i]); | 18 var loop1 = identical(obj1, parents1[i]); |
(...skipping 15 matching lines...) Expand all Loading... |
36 return _doubleEquals(obj1, obj2); | 34 return _doubleEquals(obj1, obj2); |
37 } else { | 35 } else { |
38 return obj1 == obj2; | 36 return obj1 == obj2; |
39 } | 37 } |
40 } finally { | 38 } finally { |
41 parents1.removeLast(); | 39 parents1.removeLast(); |
42 parents2.removeLast(); | 40 parents2.removeLast(); |
43 } | 41 } |
44 } | 42 } |
45 | 43 |
46 /** Returns whether [list1] and [list2] are structurally equal. */ | 44 /// Returns whether [list1] and [list2] are structurally equal. |
47 bool _listEquals(List list1, List list2, List parents1, List parents2) { | 45 bool _listEquals(List list1, List list2, List parents1, List parents2) { |
48 if (list1.length != list2.length) return false; | 46 if (list1.length != list2.length) return false; |
49 | 47 |
50 for (var i = 0; i < list1.length; i++) { | 48 for (var i = 0; i < list1.length; i++) { |
51 if (!deepEquals(list1[i], list2[i], parents1, parents2)) return false; | 49 if (!deepEquals(list1[i], list2[i], parents1, parents2)) return false; |
52 } | 50 } |
53 | 51 |
54 return true; | 52 return true; |
55 } | 53 } |
56 | 54 |
57 /** Returns whether [map1] and [map2] are structurally equal. */ | 55 /// Returns whether [map1] and [map2] are structurally equal. |
58 bool _mapEquals(Map map1, Map map2, List parents1, List parents2) { | 56 bool _mapEquals(Map map1, Map map2, List parents1, List parents2) { |
59 if (map1.length != map2.length) return false; | 57 if (map1.length != map2.length) return false; |
60 | 58 |
61 for (var key in map1.keys) { | 59 for (var key in map1.keys) { |
62 if (!map2.containsKey(key)) return false; | 60 if (!map2.containsKey(key)) return false; |
63 if (!deepEquals(map1[key], map2[key], parents1, parents2)) return false; | 61 if (!deepEquals(map1[key], map2[key], parents1, parents2)) return false; |
64 } | 62 } |
65 | 63 |
66 return true; | 64 return true; |
67 } | 65 } |
68 | 66 |
69 /** | 67 /// Returns whether two doubles are equivalent. This differs from `d1 == d2` in |
70 * Returns whether two doubles are equivalent. This differs from `d1 == d2` in | 68 /// that it considers NaN to be equal to itself. |
71 * that it considers NaN to be equal to itself. | |
72 */ | |
73 bool _doubleEquals(double d1, double d2) { | 69 bool _doubleEquals(double d1, double d2) { |
74 if (d1.isNaN && d2.isNaN) return true; | 70 if (d1.isNaN && d2.isNaN) return true; |
75 return d1 == d2; | 71 return d1 == d2; |
76 } | 72 } |
OLD | NEW |