2010-07-04 3 views
0

У меня есть файл, который я пишу некоторые java-объекты. После написания иногда мне нужно удалить некоторые из этих объектов, помещенных в позиции ramndom в файле. Есть ли способ удалить выбранный объект из файла без замены всего файла?Удаление части файла данных в java

спасибо.

ответ

5

Нет, это принципиально то, что большинство файловых систем не поддерживают. (Возможно, некоторые из них имеют специальные структуры данных, чтобы сделать их дешевыми, но большинство из них - нет, а стандартные API не поддерживают идею.)

Самый простой способ «удалить» часть файла - скопировать просто бит, который вы хотите добавить к новому файлу. Если вы только удаляете биты ближе к концу, вы можете избежать повторного копирования его снова, но для этого потребуется более сложный код.

В случае потока объектов вам, вероятно, будет лучше всего просто прочитать объекты из одного потока и написать те, которые вы все еще хотите в новом. (Очевидно, что впоследствии вы можете переименовать выходной файл.) Возможно, что, посмотрев на формат сериализации, вы могли бы избежать некоторой обработки, необходимой для повторной десериализации/сериализации, но я бы пошел по простому маршруту, чтобы начать.

2

@Jon Skeet правильный.

Мне было интересно, возможно ли технически сделать что-то, что превратит объект в последовательный поток в ... что-то еще ... путем перезаписи его соответствующим шаблоном байта. Я думаю, что ответ - нет.

Лучшее, что я мог придумать, состояло в том, чтобы перезаписать его с помощью последовательности 0x73 байт ... представление null; обратитесь к разделу Java Object Serialization Specification Chapter 6. Но есть три серьезные проблемы:

  • Перезапись с 0x73 байт будет превратить один объект в несколько null с, что бы сделать жизнь трудной для приложения пытается прочитать поток сериализованную объекта.
  • Если какие-либо другие объекты в потоке содержат ссылки на сбитый объект, эти ссылки будут разбиты, и вы получите исключение.
  • Было бы трудно определить смещения начала и байта с потоком для объектов, которые будут сбиты.

Таким образом, на практике лучший ответ - переписать поток объектов, опустив объекты, которые вы хотите удалить.

1

Вы можете попробовать использовать RandomAccessFile и перезаписать объект пробелами. Тогда в автономном режиме вы можете обрезать его.

+1

Перезапись с помощью «пробелов», скорее всего, приведет к нечитаемому/поврежденному потоку объектов. –

0

Вы можете просто пометить свой объект, чтобы сказать, что это свободное пространство, не удаляя его. Следующий объект для добавления, если он подходит, может быть вставлен в промежуток, который создал удаленный объект. Очевидно, есть вероятность, что новый объект не заполнит пробел, оставив некоторое пространство, что называется внутренней фрагментацией, и вы должны ожидать, что он будет увеличиваться со многими циклами добавления/удаления.

Время от времени выполняйте прогон «дефрагментации», чтобы упаковать все объекты, чтобы удалить все мелкие промежутки.

Смежные вопросы