Как удалить символы < ASCII из файла?
Удаление не-ASCII-символов в файле
Ответ 1
Если вы хотите использовать Perl, сделайте следующее:
perl -pi -e 's/[^[:ascii:]]//g' filename
Подробное объяснение
Следующее объяснение охватывает каждую часть вышеприведенной команды, предполагая, что читатель не знаком с чем-либо в решении...
-
perlзапустите интерпретатор perl. Perl - это язык программирования, который обычно доступен во всех подобных UNIX системах. Эта команда должна запускаться в командной строке.
-
-pФлаг
-pуказывает perl на итерацию по каждой строке входного файла, запустите указанные команды (описанные ниже) в каждой строке и затем распечатайте результат. Это эквивалентно завершению вашей программы perl вwhile(<>) { /* program... */; } continue { print; }. Там есть аналогичный флаг-n, который делает то же самое, но опускает блокcontinue { print; }, поэтому вы должны использовать его, если хотите сделать свою собственную печать. -
-iФлаг
-iуказывает perl, что входной файл должен быть отредактирован на месте, а вывод должен вернуться в этот файл. Это важно для фактического изменения файла. Опускание этого флага будет записывать вывод вSTDOUT, который затем можно перенаправить на новый файл.Примечание, которую вы не можете опустить
-iи перенаправитьSTDOUTво входной файл, так как это будет сжимать входной файл до его чтения. Это то, как работает оболочка и не имеет ничего общего с perl. Флаг-iработает вокруг этого разумно.Perl и оболочка позволяют объединить несколько одиночных параметров символа в один, поэтому мы можем использовать
-piвместо-p -iФлаг
-iпринимает один аргумент, который является расширением для использования, если вы хотите сделать резервную копию исходного файла, поэтому, если вы использовали-i.bak, тогда perl скопировал бы входной файл вfilename.bakперед внесением изменений. В этом примере я опустил создание резервной копии, потому что я ожидаю, что вы все равно будете использовать управление версиями:) -
-eФлаг
-eуказывает perl, что следующий аргумент - это полная программа perl, инкапсулированная в строку. Это не всегда хорошая идея, если у вас очень длинная программа, так как она может быть нечитаемой, но с помощью одной командной программы, как здесь, ее терпение может улучшить удобочитаемость.Примечание, что мы не можем объединить флаг
-eс флагом-i, поскольку оба они принимают один аргумент, и perl предположил бы, что второй флаг является аргументом, например, если мы использовали-ie <program> <filename>, perl предположил бы, что<program>и<filename>являются обоими входными файлами и пытаются создать<program>eи<filename>e, предполагая, чтоe- это расширение, которое вы хотите использовать для резервного копирования, Это не удастся, так как<program>не является файлом. Другой способ (-ei) также не работает, поскольку perl попытается выполнитьiкак программу, которая не скомпилирует компиляцию. -
s/.../.../Это оператор замены на основе regex. Это занимает четыре аргумента. Первое выполняется перед оператором, а если не указано, используется значение по умолчанию
$_. Второй и третий находятся между символами/. Четвертый - после окончательного/и в этом случаеg.-
$_В нашем коде первый аргумент$_, который является переменной цикла по умолчанию в perl. Как уже упоминалось выше, флаг-pобертывает нашу программу вwhile(<>), которая создает циклwhile, который считывает одну строку за раз (<>) из ввода. Он неявно назначает эту строку$_, и все команды, которые принимают один аргумент, будут использовать это, если не указано (например: просто вызовprint;будет фактически переведен наprint $_;)). Таким образом, в нашем коде операторs/.../.../работает один раз в каждой строке входного файла. -
[^[:ascii:]]Второй аргумент - это шаблон для поиска во входной строке. Этот шаблон является регулярным выражением, поэтому все, заключенное в[], является выражением скобки. Этот раздел, вероятно, является самой сложной частью этого примера, поэтому мы подробно обсудим его в конце. -
<empty string>Третий аргумент - это строка замены, которая в нашем случае является пустой строкой, так как мы хотим удалить все символы, отличные от ascii. -
gЧетвертый аргумент - это флаг модификатора для оператора подстановки. Флагgуказывает, что подстановка должна быть глобальной по всем совпадениям на входе. Без этого флага будет заменен только первый экземпляр. Другими возможными флагами являютсяiдля нечувствительных к регистру совпадений,sиm, которые применимы только к многострочным строкам (здесь есть одиночные строки),o, который указывает, что шаблон должен быть предварительно скомпилирован (что может быть полезно здесь для длинных файлов) иx, который указывает, что шаблон может включать пробелы и комментарии, чтобы сделать его более читаемым (но мы не должны писать нашу программу на одной строке, если это так).
-
-
filenameЭто входной файл, который содержит символы не-ascii, которые мы хотели бы удалить.
[^[:ascii:]]
Итак, теперь обсудим [^[:ascii:]] более подробно.
Как упоминалось выше, [] в регулярном выражении указывает выражение скобки, которое сообщает движку regex соответствовать одному символу на входе, который соответствует любому из символов в наборе символов внутри выражения. Так, например, [abc] будет соответствовать либо a, либо b или c, и он будет соответствовать только одному символу. Используя ^, поскольку первый символ инвертирует совпадение, поэтому [^abc] будет соответствовать любому одному символу, который не является a, b или c.
Но как насчет [:ascii:] внутри выражения скобки?
Если у вас установлена система на основе unix, запустите man 7 re_format в командной строке, чтобы прочитать справочную страницу. Если нет, прочитать онлайн-версию
[:ascii:] - это класс символов, который представляет весь набор символов ascii, но этот тип символьного класса может использоваться только внутри выражения скобки. Правильный способ использования этого параметра - [[:ascii:]], и он может быть отменен, как в случае с тегом abc выше, или объединен в выражении скобки с другими символами, поэтому, например, [éç[:ascii:]] будет соответствовать всем символам ascii, а также é и ç, которые не являются ascii, а [^éç[:ascii:]] будет соответствовать всем символам, которые не являются ascii, а также не é или ç.
Ответ 2
tr -dc [:graph:][:cntrl:] < input-file > cleaned-file
Предположим, что вы хотите сохранить "контрольные" символы и "печатные" символы. При необходимости скрипите.
Ответ 3
perl -pe's/[[:^ascii:]]//g' < input.txt > output.txt
Ответ 4
Вы можете написать программу на C следующим образом:
#include <stdio.h>
#include <ctype.h>
int main(int argc, char **argv)
{
FILE *fin = fopen("source_file", "rb");
FILE *fout = fopen("target_file", "w");
int c;
while ((c = fgetc(fin)) != EOF) {
if (isprint(c))
fputc(c, fout);
}
fclose(fin);
fclose(fout);
return 0;
}
Примечание. Для простоты были устранены ошибки.
Скомпилируйте его с помощью
$ gcc -W source_code.c -o convert
Запустите его с помощью
$ ./convert
Ответ 5
Мой два цента: он может не решить вашу проблему, но может дать вам несколько советов.
Команда file сообщает вам кодировку файла, то есть UTF, ASCII и т.д., и iconv может преобразовывать файл между различными кодировками.