Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(92)

Side by Side Diff: frog/leg/tree/dartstring.dart

Issue 9873021: Move frog/leg to lib/compiler/implementation. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 8 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « frog/leg/tools/mini_parser.dart ('k') | frog/leg/tree/nodes.dart » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
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
3 // BSD-style license that can be found in the LICENSE file.
4
5 /**
6 * The [DartString] type represents a Dart string value as a sequence of Unicode
7 * Scalar Values.
8 * After parsing, any valid [LiteralString] will contain a [DartString]
9 * representing its content after removing quotes and resolving escapes in
10 * its source.
11 */
12 class DartString implements Iterable<int> {
13 factory DartString.empty() => const LiteralDartString("");
14 // This is a convenience constructor. If you need a const literal DartString,
15 // use [const LiteralDartString(string)] directly.
16 factory DartString.literal(String string) => new LiteralDartString(string);
17 factory DartString.rawString(SourceString source, int length) =>
18 new RawSourceDartString(source, length);
19 factory DartString.escapedString(SourceString source, int length) =>
20 new EscapedSourceDartString(source, length);
21 factory DartString.concat(DartString first, DartString second) {
22 if (first.isEmpty()) return second;
23 if (second.isEmpty()) return first;
24 return new ConsDartString(first, second);
25 }
26 const DartString();
27 abstract int get length();
28 bool isEmpty() => length == 0;
29 abstract Iterator<int> iterator();
30 abstract String slowToString();
31
32 bool operator ==(var other) {
33 if (other is !DartString) return false;
34 DartString otherString = other;
35 if (length != otherString.length) return false;
36 Iterator it1 = iterator();
37 Iterator it2 = otherString.iterator();
38 while (it1.hasNext()) {
39 if (it1.next() != it2.next()) return false;
40 }
41 return true;
42 }
43 String toString() => "DartString#${length}:${slowToString()}";
44 abstract SourceString get source();
45 }
46
47
48 /**
49 * A [DartString] where the content is represented by an actual [String].
50 */
51 class LiteralDartString extends DartString {
52 final String string;
53 const LiteralDartString(this.string);
54 int get length() => string.length;
55 Iterator<int> iterator() => new StringCodeIterator(string);
56 String slowToString() => string;
57 SourceString get source() => new StringWrapper(string);
58 }
59
60 /**
61 * A [DartString] where the content comes from a slice of the program source.
62 */
63 class SourceBasedDartString extends DartString {
64 String toStringCache = null;
65 final SourceString source;
66 final int length;
67 SourceBasedDartString(this.source, this.length);
68 abstract Iterator<int> iterator();
69 }
70
71 /**
72 * Special case of a [SourceBasedDartString] where we know the source doesn't
73 * contain any escapes.
74 */
75 class RawSourceDartString extends SourceBasedDartString {
76 RawSourceDartString(source, length) : super(source, length);
77 Iterator<int> iterator() => source.iterator();
78 String slowToString() {
79 if (toStringCache !== null) return toStringCache;
80 toStringCache = source.slowToString();
81 return toStringCache;
82 }
83 }
84
85 /**
86 * General case of a [SourceBasedDartString] where the source might contain
87 * escapes.
88 */
89 class EscapedSourceDartString extends SourceBasedDartString {
90 EscapedSourceDartString(source, length) : super(source, length);
91 Iterator<int> iterator() {
92 if (toStringCache !== null) return new StringCodeIterator(toStringCache);
93 return new StringEscapeIterator(source);
94 }
95 String slowToString() {
96 if (toStringCache !== null) return toStringCache;
97 StringBuffer buffer = new StringBuffer();
98 StringEscapeIterator it = new StringEscapeIterator(source);
99 while (it.hasNext()) {
100 buffer.addCharCode(it.next());
101 }
102 toStringCache = buffer.toString();
103 return toStringCache;
104 }
105 }
106
107 /**
108 * The concatenation of two [DartString]s.
109 */
110 class ConsDartString extends DartString {
111 final DartString left;
112 final DartString right;
113 final int length;
114 String toStringCache;
115 ConsDartString(DartString left, DartString right)
116 : this.left = left,
117 this.right = right,
118 length = left.length + right.length;
119
120 Iterator<int> iterator() => new ConsDartStringIterator(this);
121
122 String slowToString() {
123 if (toStringCache !== null) return toStringCache;
124 toStringCache = left.slowToString().concat(right.slowToString());
125 return toStringCache;
126 }
127 SourceString get source() => new StringWrapper(slowToString());
128 }
129
130 class ConsDartStringIterator implements Iterator<int> {
131 Iterator<int> current;
132 DartString right;
133 bool hasNextLookAhead;
134 ConsDartStringIterator(ConsDartString cons)
135 : current = cons.left.iterator(),
136 right = cons.right {
137 hasNextLookAhead = current.hasNext();
138 if (!hasNextLookAhead) {
139 nextPart();
140 }
141 }
142 bool hasNext() {
143 return hasNextLookAhead;
144 }
145 int next() {
146 assert(hasNextLookAhead);
147 int result = current.next();
148 hasNextLookAhead = current.hasNext();
149 if (!hasNextLookAhead) {
150 nextPart();
151 }
152 return result;
153 }
154 void nextPart() {
155 if (right !== null) {
156 current = right.iterator();
157 right = null;
158 hasNextLookAhead = current.hasNext();
159 }
160 }
161 }
162
163 /**
164 *Iterator that returns the actual string contents of a string with escapes.
165 */
166 class StringEscapeIterator implements Iterator<int>{
167 final Iterator<int> source;
168 StringEscapeIterator(SourceString source) : this.source = source.iterator();
169 bool hasNext() => source.hasNext();
170 int next() {
171 int code = source.next();
172 if (code !== $BACKSLASH) {
173 return code;
174 }
175 code = source.next();
176 if (code === $n) return $LF;
177 if (code === $r) return $CR;
178 if (code === $t) return $TAB;
179 if (code === $b) return $BS;
180 if (code === $f) return $FF;
181 if (code === $v) return $VTAB;
182 if (code === $x) {
183 int value = hexDigitValue(source.next());
184 value = value * 16 + hexDigitValue(source.next());
185 return value;
186 }
187 if (code === $u) {
188 int value = 0;
189 code = source.next();
190 if (code === $OPEN_CURLY_BRACKET) {
191 for (code = source.next();
192 code != $CLOSE_CURLY_BRACKET;
193 code = source.next()) {
194 value = value * 16 + hexDigitValue(code);
195 }
196 return value;
197 }
198 // Four digit hex value.
199 value = hexDigitValue(code);
200 for (int i = 0; i < 3; i++) {
201 code = source.next();
202 value = value * 16 + hexDigitValue(code);
203 }
204 return value;
205 }
206 return code;
207 }
208 }
209
OLDNEW
« no previous file with comments | « frog/leg/tools/mini_parser.dart ('k') | frog/leg/tree/nodes.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698