Это явление заставляет меня задавать вопросы.
Вот подробный эксперимент, моя ОС - Windows 7 x64 SP1:
- Я изменил файл изображения (JPG) на TXT, просто изменив его расширение (или можно было просто открыть JPG с помощью блокнота, тоже самое)
Это должно выглядеть так, странно выглядящие последовательности текстов, и некоторые из них (очень редкие) на самом деле имеют смысл, как на скриншоте ниже «creator: dg-jpeg v1.0 ...»
- Я отключил перенос и выделил весь текст, используя Ctrl + A (чтобы убедиться, что ничего не пропущено)
- Я вставил скопированный текст в другой пустой текстовый файл и сохранил его как JPG, сравнил новый размер файла с оригинальным JPG. Все они (оригинального JPG, преобразованного TXT файл и вновь созданный файл TXT) имеют точный одинаковый размер, в байтах.
Когда я пытался открыть, Windows говорила: «Windows Photo Viewer не может открыть это изображение, потому что файл кажется поврежденным, поврежденным или слишком большим» .
Я даже пытался протестировать его, используя другой метод: открыл JPG с помощью блокнота, я вырезал ОДИН известный символ из легко запоминающегося места (например, первый символ 2-й строки), а затем сохранил файл. Зритель, конечно, будет отображать то же сообщение. Затем я снова открыл его и вставил символ в ТОЧНОЕ расположение (Блокнот запоминает его состояние выхода, например, положение окон, обтекание, размер шрифтов ... поэтому у меня нет проблем с получением правильной информации)
И все та же ошибка. Вы можете попробовать это, чтобы получить идею, не забудьте выбрать маленькую картинку, иначе Блокнот будет вести себя как старый ржавый человек.
Что могло быть причиной этого явления?
C:\blah>fc file1 file2
выполните команду. Возможно, файлы имеют одинаковый размер, но разные. (хотя обычно некоторые случайные изменения не дают файлу одинакового размера, но это легко может произойти). Команда fc будет очень полезна для изучения происходящего. Вы также можете использовать команду xxd, это в cygwin, а также поставляется с vim7. xxd -p file1 Это выгрузит шестнадцатеричный файл. Вы можете сравнить гекс двух файлов с этим и fc. Или даже откройте шестнадцатеричное в блокноте и пролистайте между двумя окнами блокнота с помощью alt-tab.Ответы:
В зависимости от кодировки, используемой для открытия файла, вы можете увидеть другое поведение. Мой блокнот Windows 7 позволяет открывать файлы в формате ANSI, UTF-8, Unicode или Unicode с прямым порядком байтов.
Я проверил эту проблему с помощью небольшого JPEG-изображения размером 2x2, созданного с помощью GIMP и открывающего и сохраняющего файл изображения с кодировкой ANSI. Открывая исходное и сохраненное изображение с помощью шестнадцатеричного редактора, я вижу, что все последовательности 00 (две шестнадцатеричные цифры, управляющий символ NUL ) были преобразованы в 20 (пробел).
Замена обратно в шестнадцатеричном редакторе всех 20 на 00 восстанавливает формат изображения.
Я немного погуглил и не нашел ссылок, объясняющих, почему это происходит. Только ссылка на пост, который предупреждает об этом (ссылка на кеш Google, страница недоступна).
Если вы сохраняете / открываете файл как UTF-8, кажется, что он по-прежнему преобразует символы NUL в пробелы, но также увеличивает размер получаемого файла из-за преобразования однобайтовых символов в многобайтовые последовательности UTF-8.
Если вы сохраняете / открываете файл как Unicode, кажется, что он по-прежнему преобразует символы NUL в пробелы, но также добавляет байт в начало файла, спецификацию .
источник
byte
. Возможно, вы думаете о каком-то другом языке. И разработчики приложений могут иметь дело с двоичными данными, как они считают нужным, включая использование строк C, если они того пожелают. Как я уже говорил, я могу думать о многочисленных форматах двоичных файлов, которые содержат строки C.Почему это не удается:
Блокнот создает
(ASCII code 32)
символ пробела для символов, таких как NUL,(ASCII code 0)
потому что текстовое поле Windows API допускает толькоchar *
ASCIIZ (массив символов, указатель) с нулевым символом в конце . Он отключается при первом NUL.Это происходит потому, что Windows API в основном написан на языке C, а строки с нулевым символом в конце являются одной из общих функций. Даже когда современные Windows и Unicode считаются одинаковыми, строки с нулевым символом в конце встречаются. Поэтому блокнот просто замените их пробелом, чтобы вы могли просмотреть весь файл.
Поэтому, когда вы сохраняете файл, он поврежден.
Википедия - завершенные строки
Как сделать дальнейшие исследования:
Вы можете использовать компаратор, например, вне всякого сравнения (коммерческий, пробный), чтобы увидеть эффект замены персонажа. также см. другие бинарные инструменты сравнения .
Примечание : (20) 16 = (32) 10
Причина для блокнота действует медленно на больших файлах
Он проверяет каждый символ и заменяет специальные символы пробелами. Другое программное обеспечение не выполняет преобразования в памяти (по крайней мере, не примитивно, как блокнот). Они просто по-разному отображают специальные символы. И они используют передовые методы буферизации.Глядя в Notepad.exe (32-разрядная версия XP)
(Я предполагаю, что он все еще написан на C ++ или, по крайней мере, использует сравнительно похожий компоновщик )
Я использую инструмент PEiD (который остановил разработку с введением PE + / 64 exes)
PEiD можно найти в папке bin в Universal Extractor
Я извлек блокнот. ex_ файл из Windows XP iso, очевидно. Попробуйте это. Это извлечение из CAB-файла с использованием 7z.
Предупреждение! Ваш антивирусный сканер может обнаружить Universal Extractor / PEiD как хакерские инструменты или вирусы. Не верь, не скачивай !!
Дополнительная информация о Windows API
Авторы: Джейсон С
Это не просто текстовое поле; WM_SETTEXT в общем случае не предоставляет параметров для указания длины строки, и предполагается, что строки всегда заканчиваются нулем. Вы всегда можете создать настраиваемое текстовое поле с настраиваемым сообщением, в котором указана длина строки, но Блокнот и большинство других программ этого не делают. Также функция SetWindowText также не предоставляет параметр длины.
источник
WM_SETTEXT
в общем случае не предусмотрено никаких параметров для указания длины строки, и предполагается, что строки всегда заканчиваются нулем. Вы всегда можете создать настраиваемое текстовое поле с настраиваемым сообщением, в котором указана длина строки, но Блокнот и большинство других программ этого не делают.Блокнот не сохраняет все специальные / расширенные символы в точности так, как они есть. У меня нет ссылки на это поведение под рукой, но я обнаружил, что это имеет место, например, в конце строки LF в стиле UNIX, который Notepad преобразует в CRLF, и ноль (0x00), который он игнорирует. В двоичном файле, таком как JPG, возможны случайные вхождения символов, которые Блокнот не сохраняет. Попробуйте поэкспериментировать с редактором, поддерживающим HEX, и тогда он должен работать. Я обновлю свой ответ, если найду хорошую ссылку, и когда я протестирую HEX-редактор.
Обновление: Я попробовал несколько известных редакторов-программистов, но только один из них работал сразу, HxD от Maël Hörz . Я никогда раньше не использовал HxD, но нашел его благодаря ответу на эту статью о стэке, плагину hex hex viewer / editor для Notepad ++ .
Другими редакторами, которые не работали после нескольких минут работы, были Notepad ++, Notepad2 и UltraEdit (v17.3, более старая версия). У некоторых из них были проблемы с копированием / вставкой первых нескольких байтов, магического числа подписи файла JPEG FF D8 FF. Может быть, они будут работать немного сложнее, чем у меня сейчас есть время.
источник
Раньше вы могли делать это с помощью функции «Написать обратно». Это была стандартная программа в Windows 3.1, но я не могу вспомнить, включена ли в нее Windows 95. Запись позволит в двоичном режиме безопасно редактировать любой файл, который он может открыть (возможно, очень ограниченный размер файла). Блокнот определенно не является бинарно-безопасным (текст остается тем же, но фактические байты нетекстовых символов (например, управляющих кодов) могут измениться), поэтому ваш пример JPG не работает. Попробуйте получить копию Write (и очень старой Windows) и попробуйте еще раз!
Согласно статье Википедии "Windows Write", запись была включена до Windows NT 3.5. Он был заменен Wordpad в Windows 95 и далее.
write.exe
все еще присутствовал в каталоге Windows, но был просто оболочкой для открытия Wordpad.источник
Я думаю, что это не столько проблема кодирования, сколько набор символов. Формат JPG - это в основном поток байтов. Таким образом, допускаются непечатные символы, такие как NUL, ETX, STX, SOH, DLE и т. Д.
Microsoft Notepad не может отображать эти непечатаемые символы. Он может отображать заполнители некоторого вида, такие как пробел для нулевого символа. Таким образом, открытие файла с помощью Блокнота показывает не фактическое содержимое, а содержимое, декодированное выбранной кодировкой (utf-8, utf-16 и т. Д.) И отображаемое определенным набором символов (Unicode, ASCII и т. Д.), Исключая печатные символы.
При выделении всего отображаемого текста и копировании текста в буфер обмена вы копируете только печатные символы, включая заполнители. Таким образом, автоматическое преобразование нулевых символов в пробелы и полное игнорирование других непечатных символов.
Так что в основном вы просто теряете контент, делая это таким образом. Если вместо этого вы используете hex-редактор, он полностью скопирует весь контент.
Обновление: Bhathiya Pereras ответ правильный: https://superuser.com/a/782885/322784 Непечатные символы не игнорируются при копировании текста в буфер обмена.
источник
Файл JPEG содержит нетекстовые данные, за исключением некоторых полей, в основном будут найдены любые байтовые значения от 0 до 255, особенно в области, представляющей закодированное сжатое изображение, которое содержит почти псевдослучайные данные.
Но Блокнот по умолчанию будет обрабатывать данные как текст ANSI, поэтому он будет выполнять различные действия, которые будут изменять исходные данные, как:
заменить байты, отображая специальные / неопределенные / запрещенные символы, так как они не имеют смысла для допустимого текста ANSI
перекодировать нулевые символы, конец строки и конец последовательности файлов в соглашения Windows / DOS
Это означает, что если вы отредактируете и сохраните данные как текст, это изменит jpeg в лучшем случае и сделает его непригодным для использования в худшем.
источник