Если я хочу кодировать в Rust безопасно, я должен кодировать без использования арифметики указателей? - PullRequest
0 голосов
/ 09 апреля 2019

Я читал, что арифметику указателей в Rust можно выполнить с помощью функции pointer.offset(), но она всегда должна быть реализована в unsafe code:

fn main() {
    let buf: [u32; 5] = [1, 2, 3, 4, 5];
    let mut ptr1: *const u32 = buf.as_ptr();
    unsafe {
        let ptr2: *const u32 = buf.as_ptr().offset(buf.len() as isize);
        while ptr1 < ptr2 {
            println!("Address {:?} | Value {}", ptr1, *ptr1);
            ptr1 = ptr1.offset(1);
        }
    }
}

Если я хочу кодировать в Rustбезопасно, я должен кодировать без использования арифметики указателя и просто используя соответствующий индекс массива, например?Или есть другой способ?

Ответы [ 2 ]

9 голосов
/ 09 апреля 2019

Если я хочу надежно кодировать в Rust

Тогда не стоит использовать unsafe. Есть несколько законных причин для unsafe (например, доступ к областям памяти, которые известны и безопасны для использования, например, на нескольких регистрах микроконтроллеров), но, как правило, вы не должны его использовать.

я должен кодировать, не используя арифметику указателей и просто используя соответствующий индекс массива, например

Да. Нет никакой причины (в данном конкретном случае) вообще использовать unsafe. Просто используйте

for i in 0..buf.len() {
    println!("Value {}", buf[i]);
}

Этот код, однако, не считается "ржавым", вместо этого используйте цикл for

for i in &buf {
    println!("Value {}", i);
}
7 голосов
/ 09 апреля 2019

Использование таких сырых указателей очень маловероятно [1] будет быстрее, чем идиоматический цикл for над итератором:

fn main() {
    let buf: [u32; 5] = [1, 2, 3, 4, 5];
    for val in buf.iter() {
        println!("Address {:?} | Value {}", val as *const u32, val);
    }
}

Это также намного легче для чтения и не представляет рисков для безопасности памяти.


1 Фактически, ваш код сравнивает два значения указателя на каждой итерации, поэтому он, вероятно, будет намного медленнее, чем идиоматический цикл for, который часто может пропустить все проверки границ.

...