#java #file #binary
#java #файл #двоичный
Вопрос:
Я участвую в проекте, в котором мы скрываем информацию в файле mp3, изменяя байты в указанной позиции. Я нашел в Интернете код, который позволяет мне записывать и читать байты, и я играл с ним, чтобы прочитать первые 10 байт в файле mp3.
Однако есть проблема, она продолжается до 4-го байта, после чего программа завершается. Или, другими словами, в моем цикле for это выполняется только до тех пор, пока i = 4.
Это результат, который я получаю.
Read 0th character of file: I
Read 1th character of file: D
Read 2th character of file: 3
Read 3th character of file:
Read 4th character of file:
Process completed.
На этом цикл каким-то образом заканчивается, если вы заметили, что программа должна завершиться сообщением system.out «завершение программы», но даже это не выводится. Код приведен ниже. Я пробовал с несколькими файлами mp3, и результаты те же.
В чем может быть проблема? почему моя программа завершается, даже не выдав мне сообщение об ошибке?
импортируйте java.io.File; импортируйте java.io.RandomAccessFile; импортируйте java.io.IOException;
редактировать открытый класс {
private static void doAccess() {
try {
//Reads mp3 file named a.mp3
File file = new File("a.mp3");
RandomAccessFile raf = new RandomAccessFile(file, "rw");
//In this part I try to read the first 10 bytes in the file
byte ch;
for (long i = 0; i < 10 ; i ) {
raf.seek(i); //position ourselves at position i
ch = raf.readByte(); //read the byte at position i
System.out.println("Read " i "th character of file: " (char)ch); //print the byte at that position
//repeat till position 10
}
System.out.println("End of program");
raf.close();
} catch (IOException e) {
System.out.println("IOException:");
e.printStackTrace();
}
}
public static void main(String[] args) {
doAccess();
}
}
Заранее спасибо!
Комментарии:
1. Код выглядит нормально. Должно быть, что-то еще завершает вашу программу. Что выводится
Process completed.
?2. JCreator выполняет, это всегда в конце вывода. Извините, следовало удалить эту часть, чтобы избежать путаницы: p
3. А, ладно. Хм, ваш код работает, я могу прочитать 10 байт mp3 и получить
End of program
строку.
Ответ №1:
Я только что попробовал ваш код, и у меня это работает. Проблема заключается в том, как ваша IDE обрабатывает ''
символы (4-й байт — это ''
). Чтобы увидеть реальный результат, измените инструкцию print (внутри цикла) на:
System.out.println("Read " i "th character of file: " ch);
(то есть: исключить приведение символа (char)
). Затем вы получите этот вывод:
Read 0th character of file: 73
Read 1th character of file: 68
Read 2th character of file: 51
Read 3th character of file: 3
Read 4th character of file: 0
Read 5th character of file: 0
Read 6th character of file: 0
Read 7th character of file: 0
Read 8th character of file: 15
Read 9th character of file: 118
End of program
Помимо этого я предлагаю следующее:
- Рассмотрите возможность использования готовой библиотеки для восстановления / записи метаданных MP3. Это намного лучше, чем реализация этой логики с нуля.
- Вам не нужно искать() внутри цикла. когда вы открываете файл, вы находитесь на позиции 0, и каждый ReadByte () продвигает позицию на 1.
- Код будет более читаемым, если вы переместите определение переменной ch внутрь цикла. Если вы используете его только внутри цикла, нет причин определять его снаружи.
Комментарии:
1. Большое вам спасибо! Просто удалил (char) и заставил программу работать. Я делал это так, потому что я учился его использовать. Поиск вызван тем, что в конечном итоге программа будет использовать указанные зашифрованные позиции в mp3 для чтения (скажем, сначала она прочитает байт в 24-й позиции, затем, возможно, заданной позицией будет 2056-й байт), эта информация затем будет использована для извлечения скрытого сообщения в двоичной структуре файла. Я пытался с taglib, но у меня даже не получилось написать простую программу, которая просто #включала бы одну из своих библиотек
Ответ №2:
Я запустил вашу программу, и она работает нормально. Я бы посоветовал не использовать IDE для начала, если вы не совсем уверены, что делаете. Скорее используйте командную строку.
Поместите Edit.java
и a.mp3
в ту же папку. Затем введите следующее:
javac Edit.java
java Edit
Это должно привести к правильному выводу.
Комментарии:
1. Да, так оно и было, 4-й символ был 3 в двоичном формате или как здесь написано asciitable.com символ конца файла и моя среда IDE закрыли бы причину этого, вот почему это заканчивалось так скоро. Большое спасибо за ваш ответ!
Ответ №3:
Я не вижу ничего неправильного в коде, и я не понимаю, как это могло привести к результату, о котором вы сообщаете.
Я подозреваю, что вы используете файл класса, который не соответствует исходному коду, который вы нам показали.
На самом деле в программе есть пара ошибок:
- Вы должны закрыть RAF в предложении finally.
- Приведение a
byte
к achar
является хитроумным. Очевидно, что некоторые байты не соответствуют печатным символам. Я предполагаю, что возможно, что одним из них является какой-то символ, который JCreator интерпретирует как символ конца файла…
Комментарии:
1. Спасибо за ваш ответ, JCreator, думающий, что это eof, был окончательно проблемой.