Fixed some more blatant issues
This commit is contained in:
parent
fa1ed9683b
commit
7e1b2f81b3
|
@ -942,7 +942,8 @@ impl<T: Clone> OMatrix<T, Dynamic, Dynamic> {
|
|||
where
|
||||
DefaultAllocator: Reallocator<T, Dynamic, Dynamic, Dynamic, Dynamic>,
|
||||
{
|
||||
// BEEEP!!!! BEEEEEEEP!!!
|
||||
// IMPORTANT TODO: this method is still UB, and we should decide how to
|
||||
// update the API to take it into account.
|
||||
|
||||
let placeholder = unsafe {
|
||||
Matrix::new_uninitialized_generic(Dynamic::new(0), Dynamic::new(0)).assume_init()
|
||||
|
|
|
@ -5,7 +5,7 @@ use std::io::{Result as IOResult, Write};
|
|||
use approx::{AbsDiffEq, RelativeEq, UlpsEq};
|
||||
use std::any::TypeId;
|
||||
use std::cmp::Ordering;
|
||||
use std::fmt;
|
||||
use std::fmt;use std::ptr;
|
||||
use std::hash::{Hash, Hasher};
|
||||
use std::marker::PhantomData;
|
||||
use std::mem::{self, ManuallyDrop, MaybeUninit};
|
||||
|
@ -341,6 +341,7 @@ impl<T, R, C, S> Matrix<T, R, C, S> {
|
|||
}
|
||||
}
|
||||
|
||||
/// # Memory manipulation methods.
|
||||
impl<T, R: Dim, C: Dim> OMatrix<T, R, C>
|
||||
where
|
||||
DefaultAllocator: Allocator<T, R, C>,
|
||||
|
@ -365,6 +366,7 @@ where
|
|||
}
|
||||
}
|
||||
|
||||
/// # More memory manipulation methods.
|
||||
impl<T, R: Dim, C: Dim> OMatrix<MaybeUninit<T>, R, C>
|
||||
where
|
||||
DefaultAllocator: Allocator<T, R, C>,
|
||||
|
@ -377,6 +379,18 @@ where
|
|||
<DefaultAllocator as Allocator<T, R, C>>::assume_init(self.data),
|
||||
)
|
||||
}
|
||||
|
||||
/// Assumes a matrix's entries to be initialized, and drops them. This allows the
|
||||
/// buffer to be safely reused.
|
||||
pub fn reinitialize(&mut self) {
|
||||
for i in 0..self.nrows() {
|
||||
for j in 0..self.ncols() {
|
||||
unsafe {
|
||||
ptr::drop_in_place(self.get_unchecked_mut((i, j)));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<T, R: Dim, C: Dim, S> Matrix<MaybeUninit<T>, R, C, S> {
|
||||
|
@ -447,21 +461,6 @@ impl<T, R: Dim, C: Dim, S: Storage<T, R, C>> Matrix<T, R, C, S> {
|
|||
unsafe { Self::from_data_statically_unchecked(data) }
|
||||
}
|
||||
|
||||
/// Creates a new uninitialized matrix with the given uninitialized data
|
||||
pub unsafe fn from_uninitialized_data(data: MaybeUninit<S>) -> MaybeUninit<Self> {
|
||||
// BEEP BEEP this doesn't seem good
|
||||
let res: Matrix<T, R, C, MaybeUninit<S>> = Matrix {
|
||||
data,
|
||||
_phantoms: PhantomData,
|
||||
};
|
||||
let res: MaybeUninit<Matrix<T, R, C, MaybeUninit<S>>> = MaybeUninit::new(res);
|
||||
// safety: since we wrap the inner MaybeUninit in an outer MaybeUninit above, the fact that the `data` field is partially-uninitialized is still opaque.
|
||||
// with s/transmute_copy/transmute/, rustc claims that `MaybeUninit<Matrix<T, R, C, MaybeUninit<S>>>` may be of a different size from `MaybeUninit<Matrix<T, R, C, S>>`
|
||||
// but MaybeUninit's documentation says "MaybeUninit<T> is guaranteed to have the same size, alignment, and ABI as T", which implies those types should be the same size
|
||||
let res: MaybeUninit<Matrix<T, R, C, S>> = mem::transmute_copy(&res);
|
||||
res
|
||||
}
|
||||
|
||||
/// The shape of this matrix returned as the tuple (number of rows, number of columns).
|
||||
///
|
||||
/// # Examples:
|
||||
|
@ -941,24 +940,22 @@ impl<T, R: Dim, C: Dim, S: Storage<T, R, C>> Matrix<T, R, C, S> {
|
|||
/// Folds a function `f` on each entry of `self`.
|
||||
#[inline]
|
||||
#[must_use]
|
||||
pub fn fold<Acc>(&self, init: Acc, mut f: impl FnMut(Acc, T) -> Acc) -> Acc
|
||||
pub fn fold<Acc>(&self, mut init: Acc, mut f: impl FnMut(Acc, T) -> Acc) -> Acc
|
||||
where
|
||||
T: Clone,
|
||||
{
|
||||
let (nrows, ncols) = self.data.shape();
|
||||
|
||||
let mut res = init;
|
||||
|
||||
for j in 0..ncols.value() {
|
||||
for i in 0..nrows.value() {
|
||||
unsafe {
|
||||
let a = self.data.get_unchecked(i, j).clone();
|
||||
res = f(res, a)
|
||||
init = f(init, a)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
res
|
||||
init
|
||||
}
|
||||
|
||||
/// Folds a function `f` on each pairs of entries from `self` and `rhs`.
|
||||
|
@ -967,7 +964,7 @@ impl<T, R: Dim, C: Dim, S: Storage<T, R, C>> Matrix<T, R, C, S> {
|
|||
pub fn zip_fold<T2: Clone, R2: Dim, C2: Dim, S2, Acc>(
|
||||
&self,
|
||||
rhs: &Matrix<T2, R2, C2, S2>,
|
||||
init: Acc,
|
||||
mut init: Acc,
|
||||
mut f: impl FnMut(Acc, T, T2) -> Acc,
|
||||
) -> Acc
|
||||
where
|
||||
|
@ -976,7 +973,6 @@ impl<T, R: Dim, C: Dim, S: Storage<T, R, C>> Matrix<T, R, C, S> {
|
|||
ShapeConstraint: SameNumberOfRows<R, R2> + SameNumberOfColumns<C, C2>,
|
||||
{
|
||||
let (nrows, ncols) = self.data.shape();
|
||||
let mut res = init;
|
||||
|
||||
assert_eq!(
|
||||
(nrows.value(), ncols.value()),
|
||||
|
@ -989,12 +985,12 @@ impl<T, R: Dim, C: Dim, S: Storage<T, R, C>> Matrix<T, R, C, S> {
|
|||
unsafe {
|
||||
let a = self.data.get_unchecked(i, j).clone();
|
||||
let b = rhs.data.get_unchecked(i, j).clone();
|
||||
res = f(res, a, b)
|
||||
init = f(init, a, b)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
res
|
||||
init
|
||||
}
|
||||
|
||||
/// Replaces each component of `self` by the result of a closure `f` applied on it.
|
||||
|
|
|
@ -59,7 +59,6 @@ impl<T, R: Dim, C: Dim, S: Storage<T, R, C>> Matrix<T, R, C, S> {
|
|||
}
|
||||
|
||||
/// Returns a column vector resulting from the folding of `f` on each column of this matrix.
|
||||
// BEEEEP!!!! Pretty sure there's something fishy here.
|
||||
#[inline]
|
||||
#[must_use]
|
||||
pub fn compress_columns(
|
||||
|
|
|
@ -42,23 +42,24 @@ where
|
|||
// extra allocations.
|
||||
let (nrows, ncols) = self.data.shape();
|
||||
let mut multiplier = self.clone_owned();
|
||||
|
||||
// TODO: ACTUALLY MAKE BUF USEFUL! BEEEEEEEEP!!
|
||||
let mut buf = Matrix::new_uninitialized_generic(nrows, ncols);
|
||||
|
||||
// Exponentiation by squares.
|
||||
loop {
|
||||
if e % two == one {
|
||||
let mut buf = Matrix::new_uninitialized_generic(nrows, ncols);
|
||||
self.mul_to(&multiplier, &mut buf);
|
||||
let buf = unsafe { buf.assume_init() };
|
||||
self.copy_from(&buf);
|
||||
unsafe {
|
||||
self.copy_from(&buf.assume_init_ref());
|
||||
}
|
||||
buf.reinitialize();
|
||||
}
|
||||
|
||||
e /= two;
|
||||
let mut buf = Matrix::new_uninitialized_generic(nrows, ncols);
|
||||
multiplier.mul_to(&multiplier, &mut buf);
|
||||
let buf = unsafe { buf.assume_init() };
|
||||
multiplier.copy_from(&buf);
|
||||
unsafe {
|
||||
multiplier.copy_from(&buf.assume_init_ref());
|
||||
}
|
||||
buf.reinitialize();
|
||||
|
||||
if e == zero {
|
||||
return true;
|
||||
|
|
|
@ -264,7 +264,9 @@ where
|
|||
pub fn new_uninitialized_generic(nrows: R, ncols: C, nvals: usize) -> Self {
|
||||
let mut i = Vec::with_capacity(nvals);
|
||||
|
||||
//BEEP BEEP!!!! UNDEFINED BEHAVIOR ALERT!!! BEEP BEEEP!!!
|
||||
// IMPORTANT TODO: this method is still UB, and we should decide how to
|
||||
// update the API to take it into account.
|
||||
|
||||
unsafe {
|
||||
i.set_len(nvals);
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue