Это не ошибка компилятора, и эта проблема не связана с вашим использованием дженериков. И First
, и Last
являются функциями, поэтому компилятор не может сказать, хотите ли вы их назвать или ссылаться на них. Будьте ясны и дайте компилятору понять, что вы хотите вызвать функцию, поставив парсеры.
aProc := ProcList.First();
aProc := ProcList.Last();
Еще раз вы были пойманы решением разрешить игнорировать парс при вызове процедур и функций , Это дизайнерское решение, в то время как выглядело так привлекательно, когда оно было сделано, выглядит менее так, что процедурные типы настолько широко используются в современных стилях кодирования.
Когда вы пишете ProcList.First
, компилятор сталкивается с двусмысленностью. Вы хотите назвать функцию, или хотите ли вы обратиться к функции как процедурный? Во многих сценариях компилятор не может разрешить двусмысленность, но здесь это не так, где выражение найдено в правой части оператора присваивания. Столкнувшись с этой неоднозначностью, компилятор предполагает, что вы имеете в виду ссылку на функцию.
Он принимает этот выбор, потому что другой выбор будет хуже. По крайней мере, таким образом вы можете предоставить parens и явно указать, что вы имеете в виду функцию вызываемой функции. Если бы компилятор пошел другим путем, тогда вам оставалось искать способ сказать, что вы хотели бы обратиться к функции.
В качестве окончательного в стороне, если First
и Last
были реализованы как свойства, не было бы никакой двусмысленности.
Связанная выше функция недостаточна. Он не может экранировать ^
или $
(начало и конец строки) или -
, которые в группе символов используются для диапазонов.
Используйте эту функцию:
RegExp.escape= function(s) {
return s.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&');
};
Хотя это может показаться ненужным на первый взгляд, экранирование -
(а также ^
) делает функцию пригодной для экранирования символов, которые будут вставлены в класс символов, а также тело регулярного выражения.
Экранирование /
делает функцию подходящей для экранирования символов, которые будут использоваться в литерале регулярного выражения JS для последующей оценки.
Поскольку у экранирования любого из них нет недостатков, имеет смысл экранировать, чтобы охватить более широкие варианты использования.
И да, досадно, что это не является частью стандартного JavaScript.
Другой (намного более безопасный) подход должен выйти из всех символов (и не всего несколько специальных, которые мы в настоящее время знаем), использование формата \u{code}
Escape unicode:
function escapeRegExp(text) {
return Array.from(text)
.map(char => `\\u{${char.charCodeAt(0).toString(16)}}`)
.join('');
}
console.log(escapeRegExp('a.b')); // '\u{61}\u{2e}\u{62}'
Обратите внимание на то, что необходимо передать эти u
флаг для этого метода для работы:
var expression = new RegExp(escapeRegExp(usersString), 'u');
Только когда-либо был и когда-либо будут 12 метасимволов, которых нужно оставить
, чтобы считаться литералом.
не имеет значения, что сделано с завершенной строкой, вставленной в сбалансированный
, regex обертка, добавленная, не имеет значения.
Делают строковую замену с помощью этого
var escaped_string = oldstring.replace( /[\\^$.|?*+()[{]/g, '\\[110]amp;' );