我正在使用这个for循环:
for (var elem in sortedTokens){
if (elem.identifier == "ACCESSOR"){
//
}
else if (elem.identifier == "PROPERTY"){
// Check the identifier of the next element
}
}
我如何能够访问其中的下一个元素?到目前为止,我总是使用带有Dart索引的while循环。这样做的正确方法是什么?
由于
答案 0 :(得分:2)
在处理当前元素时,您无法访问for-in
迭代的下一个元素。
像for-in
这样的for (var elem in sortedTokens) { ... }
循环大致相当于:
for (var it = sortedTokens.iterator; it.moveNext();) {
var elem = it.current;
...
}
如您所见,移动到下一个元素的moveNext
仅在当前元素的主体完成时执行。
因此,如果不进行某些解决方法,就无法使用for-in
执行您想要的操作。 for-in
针对每个元素进行了优化,而不是为了无序访问元素。
最简单的解决方法是无论如何都要使用索引。如果你真的需要向前或向后看,或者在某些情况下更快一步,那就没有错了。
另一种解决方法可能是:
bool isProperty = false;
for (var elem in sortedTokens) {
if (isProperty) {
// check the identifier of the current element
isProperty = false;
continue;
}
if (elem.identifier == "ACCESSOR") {
//
} else if (elem.identifier == "PROPERTY") {
isProperty = true;
}
}
这只是保持元素之间的状态(这里只是一个布尔值),所以下一个元素知道你想用它做什么。 在某些情况下这是有用和方便的(比如构建一个以逗号分隔的列表,你想要特殊情况下第一个元素不添加逗号),在其他情况下,它比它的价值更麻烦,因为状态变得笨拙并且逻辑错综复杂。
答案 1 :(得分:1)
您可能想要使用常规for循环:
for (int i = 0; i < sortedTokens.length; i++){
var elem = sortedTokens[i];
if (elem.identifier == "ACCESSOR"){
//
}
else if (elem.identifier == "PROPERTY"){
if (i+1 < sortedTokens.length) {
var nextElem = sortedTokens[i+1];
// Check the identifier of the next element
}
}
}
但你可以更进一步,包装该功能:
void forEach<T>(List<T> list, void action(T current, T next)) {
for (var i = 0; i < list.length; i++) {
T current = list[i];
T next = i+1 < list.length ? list[i+1] : null;
action(current, next);
}
}
forEach (sortedTokens, (elem, next) {
if (elem.identifier == "ACCESSOR"){
//
}
else if (elem.identifier == "PROPERTY"){
if (next != null) {
// Check the identifier of the next element
}
}
});
工作DartPad示例