ocaml sdl сборка мусора - PullRequest
       10

ocaml sdl сборка мусора

1 голос
/ 02 апреля 2012

Итак, вот в чем дело: сначала я подумал, что следующий код был действительно сексуальным для воспроизведения, а затем для освобождения файла wav после его завершения, без остановки машины с помощью команды задержки (при условии, что программа выполняет и будет выполнять какие-то действия). для продолжительности wav-файла, то есть, не выходя, когда вызывается функция):

let rec play_wav file play =
   Sdlmixer.open_audio ~freq:44100 ();
   let loaded_file = Sdlmixer.loadWAV file in
   if play = false then
     Sdlmixer.free_chunk loaded_file
   else 
     (
       Sdlmixer.play_channel ~loops:1 loaded_file;
       play_wav file false
     )
 ;;

Я должен также сказать, что, вероятно, есть лучшие способы выполнить ту же задачу, и она могла бы работать только из-за особенностей машины и т. Д., Но теперь у меня есть лишь академический интерес к вопросу:

(1) файл загружается дважды и освобождается только один раз, создавая таким образом совершенно неуместный код;

или, наоборот,

(2), является ли файл wav, загруженный дважды с помощью Sdlmixer.loadWAV, не , которому назначены два отдельных адреса памяти, malloc и т. Д., Или в логике разделения h = (h1 * emp ) является пост-условием;) Другими словами, если однажды загрузить его, его загрузка снова неэффективна, и одно свободное освобождение освободит чанк, независимо от того, сколько раз он был загружен.

и, наконец,

(3) Sdlmixer.free_chunk даже необходим, поскольку аналогичная функция C free_surface для библиотек OCaml-sdl не реализована.

Запуск valgrind для всего нижеприведенного не указывает на утечки памяти:

(a) программа, содержащая функцию play_wav,

(b) с функцией, которая не освобождает чанк,

(c) с последовательным блоком кода load-play-wait-free_chunk,

(d) с функцией, которая загружает один и тот же файл WAV 1000 раз.

(На самом деле, технически, в каждом случае говорится «определенно потеряно: 337 байт в 4 блоках», не уверен, о чем идет речь, но независимо от того, что valgrind сообщает одинаковые результаты памяти для всех четырех случаев.)

Я предполагаю, что в случае (b) сборщик мусора OCaml позаботится об этом, когда программа завершится, поэтому сложно сказать, все еще загружена ли она и занимает ли она память после завершения этой конкретной подпрограммы, и, следовательно, нуждается в освобождении, так как, когда функция завершает выполнение программы, поэтому, вероятно, было бы неплохо использовать функцию свободного чанка в больших программах.

Во всяком случае, просто было интересно, что люди могут думать и мнения по этому поводу.

1 Ответ

1 голос
/ 26 октября 2012

Из-за просмотра исходного кода библиотеки мне кажется, что значения чанков не собираются автоматически, поэтому вы должны явно освободить их или настроить для этого собственный обработчик (см. Gc.finalize).

Мне странно, что valgrind не сообщает о какой-либо существенной проблеме.

Ваш код действительно загружает семпл дважды, если параметр play имеет значение true при первоначальном вызове. Я полагаю, вам нужен параметр воспроизведения, за исключением того факта, что вы используете его, чтобы остановить и выпустить семпл в функции.

Возможно, что-то вроде:

let play_wav = function
     true -> (fun file ->
     Sdlmixer.open_audio ~freq:44100 ();
     let loaded_file = Sdlmixer.loadWAV file in
     Sdlmixer.play_channel ~loops:1 loaded_file;
     Sdlmixer.delay 1000;
     Sdlmixer.free_chunk loaded_file;
     Sdlmixer.close_audio ())
    | _   -> (fun _ -> ())

может соответствовать вашим потребностям. Я поменял местами два параметра play_wav, чтобы сделать для компилятора более очевидным, что ему нечего делать, когда play имеет значение false. Если вы передадите false явно, функция должна быть оптимизирована (я считаю). Я добавил отсутствующий вызов close_audio и задержку, чтобы дать микшеру некоторое время для воспроизведения семпла. Теперь, если вам нужно воспроизвести один и тот же семпл много раз, было бы более интересно кешировать его, чтобы избежать его перезагрузки позже.

...