Тема: JScript: поиск и замена текста по регулярным выражениям
Фильтр текста по регулярным выражениям (регэкспам). Работать с ним только через cscript.exe.
Обрабатывает переданный по конвейеру текст заданным регулярным выражением и
выводит в выходной поток.
Может следующее:
- вывести список подстрок, совпадающих с регулярным выражением.
- вывести текст, удалив текст, совпадающий с регулярным выражением (ключ "r")
- вывести текст, заменив текст, совпадающий с регулярным выражением
на свой текст (ключ "r") Поддерживаются переменные замены (match variables).
cscript.exe strfilt.js </регулярное выражение/[ключи]> [замена]
Помимо стандартных ключей WSH (i,m,g) введен новый ключ "r". Он указывает,
учитывать ли строку замены
Регулярное выражение или строка замены заключаются в кавычки, если в них есть пробелы.
Примеры:
echo 001234-5699 | cscript.exe strfilt.js "/(\d{4})\-(\d{2})/igr" "$2 = $1"
echo 001234-5699 | cscript.exe strfilt.js "/(\d{4})/i"
echo 001234-5699 | cscript.exe strfilt.js "/(\d{4})/ig"
Полное описание синтаксиса регулярных выражений можно найти в документации Microsoft по WSH:
http://download.microsoft.com/download/ … ript56.chm
Этот же хелп выдается, если запустить скрипт без параметров.
Я этот скрипт использую в EditPlus - там есть возможность обрабатывать открытый файл с помощью текстовых фильтров - утилит, которые принимают текст по конвейеру и выводят результат в stdout.
try {
var WSH = new ActiveXObject ('WScript.Shell');
var Arg = WScript.Arguments;
var reg = new RegExp('.', '');
var input = '';
var repl = '';
var sr = '';
// Если скрипт запущен через WScript, ругаемся и выходим
if (WScript.FullName.toLowerCase() == (WScript.Path+'\\wscript.exe').toLowerCase()) {
WSH.Popup('Запуск сценария производится только через '+WScript.Path+'\\cscript.exe.\n\nВыходим...', 0, 'Ошибка', 16);
WScript.Quit();
}
if (Arg.length == 0) {
WScript.StdOut.WriteLine(
'Фильтр текста по регулярным выражениям (регэкспам)\n\n'+
'Обрабатывает переданный по конвейеру текст заданным регулярным выражением и\nвыводит в выходной поток.\n\n'+
'Может следующее:\n'+
'\t- вывести список подстрок, совпадающих с регулярным выражением.\n'+
'\t- вывести текст, удалив текст, совпадающий с регулярным выражением (ключ "r")\n'+
'\t- вывести текст, заменив текст, совпадающий с регулярным выражением\n\tна свой текст (ключ "r") Поддерживаются переменные замены (match variables).\n\n'+
'cscript.exe '+WScript.ScriptName+' </регулярное выражение/[ключи]> [замена]\n\n'+
'Помимо стандартных ключей WSH (i,m,g) введен новый ключ "r". Он указывает,\nучитывать ли строку замены\n'+
'Регулярное выражение или строка замены заключаются в кавычки, если в них есть пробелы.\n'+
'Примеры:\n\n'+
'echo 001234-5699 | cscript.exe '+WScript.ScriptName+' "/(\\d{4})\\-(\\d{2})/igr" "$2 = $1"\n'+
'echo 001234-5699 | cscript.exe '+WScript.ScriptName+' "/(\\d{4})/i"\n'+
'echo 001234-5699 | cscript.exe '+WScript.ScriptName+' "/(\\d{4})/ig"\n\n'+
'Полное описание синтаксиса регулярных выражений можно найти в документации Microsoft по WSH:\nhttp://download.microsoft.com/download/9/1/d/91dfd1b3-a274-4e17-a376-f605ff39c58c/script56.chm');
WScript.Quit();
}
// из входных параметров вычленяем регулярное выражение, ключи к нему и строку замены (если указана)
var re = Arg(0).match(/\/(.+)\/([imgr]{1,4})?/i)
if (re) {
// стандартные флаги Regexp Object - g (global) i (ignorecase) m (multiline)
// вводим свой флаг - "r" (учитывать строку замены)
var toRepl = (Arg.length>=2)?( Arg(1) ):(''); // строка замены для ключа "r"
var isRepl = (re[2].search('r') >= 0); // заменить найденное в тексте на содержимое третьего параметра.
// Если третий параметр не указан, это равноценно удалению найденного
var isBlk = (re[2].search('m') < 0); // искать не построчно а во всем тексте сразу
var isGlob = (re[2].search('g') >= 0); // g - глобальная замена
re[2] = re[2].replace(/r/ig,'')+''; // поскольку наш ключ самопальный, выкидываем его, а то WSH им подавится
reg.compile(re[1], re[2]); // Compiles a regular expression into an internal format for faster execution.
} else {
WSH.Popup("Регулярное выражение записано с ошибкой",0,'Ошибка выполнения',16+0);
WScript.Quit();
}
if (isBlk){
// обрабатывать весь текст одновременно
while (!WScript.StdIn.AtEndOfStream) {
input += WScript.StdIn.ReadAll();
}
Process(input)
} else {
// работать построчно
while (!WScript.StdIn.AtEndOfStream) {
input = WScript.StdIn.ReadLine();
Process(input)
}
}
input = null;
} catch(e) {
WSH.Popup(e.description,0,'Ошибка выполнения',16+0);
}
function Process(){
if (isRepl) {
// заменять найденное
WScript.StdOut.Write( input.replace(reg, toRepl) + ((!isBlk) ? '\n' : '') );
} else {
// вывести только найденное
if ( sr = input.match(reg) ) {
if (isGlob){
// If the global flag is set, elements 0 - n contain all matches that occurred. (MS Help)
// Выводим весь список совпавших подстрок
for(var i=0; i<sr.length; i++) {
WScript.StdOut.WriteLine(sr[i]);
}
} else {
// If the global flag (g) is not set, Element zero of the array contains the entire match,
// while elements 1 – n contain any submatches that have occurred within the match. (MS Help)
// Выводим первую попавшуюся подстроку
WScript.StdOut.WriteLine(sr[0]);
}
}
}
}