В ClaiR (пока) невозможно записать изменения, сделанные в AST, обратно в файл. По этой причине я создаю список lrel[int, int, str] changes = [];
с начальной и конечной позициями удаляемой подстроки и строкой, которую необходимо заменить.
Когда у меня есть полный список изменений, которые я хочу внести в исходный файл, я сортирую изменения и открываю файл с помощью fb = chars(readFile(f));
, чтобы внести изменения
public list[int] changeCharList(list[int] charList, lrel[int, int, str] changesList) {
int offset = 0;
for (t <- [0 .. size(changesList)]) {
tuple[int startIndex, int endIndex, str changeWithString] change = changesList[t];
int startIndexWithOffset = change.startIndex + offset;
int endIndexWithOffset = change.endIndex + offset;
list[int] changeWithChars = chars(change.changeWithString);
for (i <- [startIndexWithOffset .. endIndexWithOffset]) {
charList = delete(charList, startIndexWithOffset);
}
for (i <- [0 .. size(changeWithChars)]) {
charList = insertAt(charList, startIndexWithOffset + i, changeWithChars[i]);
}
offset += size(changeWithChars) - (change.endIndex - change.startIndex);
}
return charList;
}
и запись в файл writeFileBytes(f, fb);
Этот подход работает для исходных файлов без расширенных макросов, но не работает для исходных файлов с расширенными макросами. В последнем случае смещения, используемые в AST, не сопоставляют смещения с файлом, открытым с использованием readFile
.
В качестве обходного пути я могу комментировать макросы перед запуском Rascal и раскомментировать их после запуска Rascal. Мне это не нравится.
Есть ли способ пересчитать смещения таким образом, чтобы смещения AST отображали смещения чтения файла?