Comments 15
К сожалению, не понял из статьи, зачем в рассматриваемом кейсе именно неуправляемый массив.
0
Один из подводных камней, видимо, выравнивание полей в структурах.
+1
Мне так показалось, что это всё скорее нужно для сопряжения с кодом на Си, для написания над ним безопасных оберток. А ещё мне кажется, что лучше бы разрешали пользоваться такими штуками внутри блока unsafe, а то сейчас по коду:
Становится неясно безопасно у нас всё или нет (мало ли кто решил обозвать свойство именем memory). Итого этот UnsafeMutablePointer может радостно по всему коду расползтись.
let pSize = UnsafeMutablePointer<GifSize>(p)
// пусть тут будет 10000 строчек ещё
NSLog("Gif width = \(pSize.memory.width), height = \(pSize.memory.height)")
Становится неясно безопасно у нас всё или нет (мало ли кто решил обозвать свойство именем memory). Итого этот UnsafeMutablePointer может радостно по всему коду расползтись.
+1
Да, вы правы если pSize будет иметь время жизни большее чем data то это приведет к чтению освобожденной памяти. Так что применяя указатели нужно быть очень внимательным.
0
Поэтому в Rust указатели могут быть использованы только внутри unsafe блока, а если они там были объявлены, то они его и покинуть не смогут. То есть ногу прострелить становится сложнее.
+3
> в Rust указатели могут быть использованы только внутри unsafe блока
Смотря как понимать «использованы» — сырые указатели можно брать и передавать где угодно, вот разыменовать можно только в `unsafe{}`.
> а если они там были объявлены, то они его и покинуть не смогут
Не, сырые указатели можно куда угодно передавать же, в том числе и из блока:
https://play.rust-lang.org/?gist=17f0da2b3d478e51e0b7&version=stable
Смотря как понимать «использованы» — сырые указатели можно брать и передавать где угодно, вот разыменовать можно только в `unsafe{}`.
> а если они там были объявлены, то они его и покинуть не смогут
Не, сырые указатели можно куда угодно передавать же, в том числе и из блока:
https://play.rust-lang.org/?gist=17f0da2b3d478e51e0b7&version=stable
0
В Java для ускорения критически важных участков кода используют. Быть может, и тут получится.
0
0
Могли бы вы пояснить на каком-то другом примере преимущества от подобных операций — на чем реально можно много сэкономить ресурсов.
Просто в данном случае размер картинки, конечно, удалось получить без каких-либо сторонних библиотек, но для другого программиста данный код в проекте может вызвать больше вопросов. Тут выгода не так очевидна, на мой взгляд.
Просто в данном случае размер картинки, конечно, удалось получить без каких-либо сторонних библиотек, но для другого программиста данный код в проекте может вызвать больше вопросов. Тут выгода не так очевидна, на мой взгляд.
0
let p = UnsafeMutablePointer<Int>.alloc(1) p.memory = 20 p.dealloc(1)
Во второй строчке следует использовать метод initialize(), так как память ещё не инициализирована. Только после этого можно работать с memory. До того, как освобождать память, следует вызвать метод destroy().
Память, на которую указывает Unsafe(Mutable)Pointer, может быть инициализирована или нет. Очень важно использовать правильные методы для памяти в различных состояниях. Так как ваш указатель указывает на Int, то скорее всего в этом конкретном случае ничего плохого не случится, но как только вы начнёте работать с типами, для которых копия экземпляра не создаётся тривиальным побитовым копированием, не использование правильных методов почти наверняка приведёт к падениям программы и утечкам памяти. Посмотрите документацию на UnsafeMutablePointer, там довольно подробно написано про состояния, в которых он может находиться.
Тем не менее подобный низкоуровневый код в некоторых случаях позволяет оптимизировать программу либо по скорости, либо по количеству используемой памяти.
Чаще всего прямая работа с указателями нужна для вызова API на C, которые принимают сложные структуры данных с указателями внутри.
0
Sign up to leave a comment.
Unsafe в Swift