Skip to content

Commit f8e2fc0

Browse files
committed
Merge pull request #8 from bluss/general-backend
Introduce ArrayBase and provide both Array, OwnedArray, ArrayView and ArrayViewMut
2 parents 42a450f + 5842355 commit f8e2fc0

File tree

4 files changed

+939
-337
lines changed

4 files changed

+939
-337
lines changed

src/arrayformat.rs

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,15 @@
11
use std::fmt;
22
use super::{Array, Dimension};
3+
use super::{
4+
ArrayBase,
5+
Data,
6+
};
37

4-
fn format_array<A, D: Dimension, F>(view: &Array<A, D>, f: &mut fmt::Formatter,
5-
mut format: F) -> fmt::Result where
6-
F: FnMut(&mut fmt::Formatter, &A) -> fmt::Result,
8+
fn format_array<A, S, D, F>(view: &ArrayBase<S, D>, f: &mut fmt::Formatter,
9+
mut format: F) -> fmt::Result
10+
where F: FnMut(&mut fmt::Formatter, &A) -> fmt::Result,
11+
D: Dimension,
12+
S: Data<Elem=A>,
713
{
814
let ndim = view.dim.slice().len();
915
/* private nowadays
@@ -80,7 +86,8 @@ impl<'a, A: fmt::Display, D: Dimension> fmt::Display for Array<A, D>
8086
}
8187
}
8288

83-
impl<'a, A: fmt::Debug, D: Dimension> fmt::Debug for Array<A, D>
89+
impl<'a, A: fmt::Debug, S, D: Dimension> fmt::Debug for ArrayBase<S, D>
90+
where S: Data<Elem=A>,
8491
{
8592
/// Format the array using `Debug` and apply the formatting parameters used
8693
/// to each element.

src/arraytraits.rs

Lines changed: 90 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -9,46 +9,63 @@ use std::ops::{
99
IndexMut,
1010
};
1111

12-
use super::{Array, Dimension, Ix, Elements, ElementsMut};
12+
use super::{
13+
Array, Dimension, Ix, Elements, ElementsMut,
14+
ArrayBase,
15+
ArrayView,
16+
ArrayViewMut,
17+
Data,
18+
DataMut,
19+
};
1320

14-
impl<'a, A, D: Dimension> Index<D> for Array<A, D>
21+
/// Access the element at **index**.
22+
///
23+
/// **Panics** if index is out of bounds.
24+
impl<S, D> Index<D> for ArrayBase<S, D>
25+
where D: Dimension,
26+
S: Data,
1527
{
16-
type Output = A;
28+
type Output = S::Elem;
1729
#[inline]
18-
/// Access the element at **index**.
19-
///
20-
/// **Panics** if index is out of bounds.
21-
fn index(&self, index: D) -> &A {
22-
self.at(index).expect("Array::index: out of bounds")
30+
fn index(&self, index: D) -> &S::Elem {
31+
self.get(index).expect("Array::index: out of bounds")
2332
}
2433
}
2534

26-
impl<'a, A: Clone, D: Dimension> IndexMut<D> for Array<A, D>
35+
/// Access the element at **index** mutably.
36+
///
37+
/// **Panics** if index is out of bounds.
38+
impl<S, D> IndexMut<D> for ArrayBase<S, D>
39+
where D: Dimension,
40+
S: DataMut,
2741
{
2842
#[inline]
29-
/// Access the element at **index** mutably.
30-
///
31-
/// **Panics** if index is out of bounds.
32-
fn index_mut(&mut self, index: D) -> &mut A {
33-
self.at_mut(index).expect("Array::index_mut: out of bounds")
43+
fn index_mut(&mut self, index: D) -> &mut S::Elem {
44+
self.get_mut(index).expect("Array::index_mut: out of bounds")
3445
}
3546
}
3647

3748

38-
impl<A: PartialEq, D: Dimension>
39-
PartialEq for Array<A, D>
49+
impl<S, S2, D> PartialEq<ArrayBase<S2, D>> for ArrayBase<S, D>
50+
where D: Dimension,
51+
S: Data,
52+
S2: Data<Elem = S::Elem>,
53+
S::Elem: PartialEq,
4054
{
4155
/// Return `true` if the array shapes and all elements of `self` and
4256
/// `other` are equal. Return `false` otherwise.
43-
fn eq(&self, other: &Array<A, D>) -> bool
57+
fn eq(&self, other: &ArrayBase<S2, D>) -> bool
4458
{
4559
self.shape() == other.shape() &&
4660
self.iter().zip(other.iter()).all(|(a, b)| a == b)
4761
}
4862
}
4963

50-
impl<A: Eq, D: Dimension>
51-
Eq for Array<A, D> {}
64+
impl<S, D> Eq for ArrayBase<S, D>
65+
where D: Dimension,
66+
S: Data,
67+
S::Elem: Eq,
68+
{ }
5269

5370
impl<A> FromIterator<A> for Array<A, Ix>
5471
{
@@ -58,35 +75,59 @@ impl<A> FromIterator<A> for Array<A, Ix>
5875
}
5976
}
6077

61-
impl<'a, A, D> IntoIterator for &'a Array<A, D> where
62-
D: Dimension,
78+
impl<'a, S, D> IntoIterator for &'a ArrayBase<S, D>
79+
where D: Dimension,
80+
S: Data,
6381
{
64-
type Item = &'a A;
65-
type IntoIter = Elements<'a, A, D>;
82+
type Item = &'a S::Elem;
83+
type IntoIter = Elements<'a, S::Elem, D>;
6684

67-
fn into_iter(self) -> Self::IntoIter
68-
{
85+
fn into_iter(self) -> Self::IntoIter {
6986
self.iter()
7087
}
7188
}
7289

73-
impl<'a, A, D> IntoIterator for &'a mut Array<A, D> where
74-
A: Clone,
75-
D: Dimension,
90+
impl<'a, S, D> IntoIterator for &'a mut ArrayBase<S, D>
91+
where D: Dimension,
92+
S: DataMut,
7693
{
77-
type Item = &'a mut A;
78-
type IntoIter = ElementsMut<'a, A, D>;
94+
type Item = &'a mut S::Elem;
95+
type IntoIter = ElementsMut<'a, S::Elem, D>;
7996

8097
fn into_iter(self) -> Self::IntoIter
8198
{
8299
self.iter_mut()
83100
}
84101
}
85102

86-
impl<A: hash::Hash, D: Dimension>
87-
hash::Hash for Array<A, D>
103+
impl<'a, A, D> IntoIterator for ArrayView<'a, A, D>
104+
where D: Dimension,
88105
{
89-
fn hash<S: hash::Hasher>(&self, state: &mut S)
106+
type Item = &'a A;
107+
type IntoIter = Elements<'a, A, D>;
108+
109+
fn into_iter(self) -> Self::IntoIter {
110+
self.into_iter_()
111+
}
112+
}
113+
114+
impl<'a, A, D> IntoIterator for ArrayViewMut<'a, A, D>
115+
where D: Dimension,
116+
{
117+
type Item = &'a mut A;
118+
type IntoIter = ElementsMut<'a, A, D>;
119+
120+
fn into_iter(self) -> Self::IntoIter {
121+
self.into_iter_()
122+
}
123+
}
124+
125+
impl<'a, S, D> hash::Hash for ArrayBase<S, D>
126+
where D: Dimension,
127+
S: Data,
128+
S::Elem: hash::Hash,
129+
{
130+
fn hash<H: hash::Hasher>(&self, state: &mut H)
90131
{
91132
self.shape().hash(state);
92133
for elt in self.iter() {
@@ -95,6 +136,22 @@ hash::Hash for Array<A, D>
95136
}
96137
}
97138

139+
// NOTE: ArrayBase keeps an internal raw pointer that always
140+
// points into the storage. This is Sync & Send as long as we
141+
// follow the usual inherited mutability rules, as we do with
142+
// Vec, &[] and &mut []
143+
144+
/// `ArrayBase` is `Sync` when the storage type is.
145+
unsafe impl<S, D> Sync for ArrayBase<S, D>
146+
where S: Sync + Data, D: Sync
147+
{ }
148+
149+
/// `ArrayBase` is `Send` when the storage type is.
150+
unsafe impl<S, D> Send for ArrayBase<S, D>
151+
where S: Send + Data, D: Send
152+
{ }
153+
154+
98155
#[cfg(feature = "rustc-serialize")]
99156
// Use version number so we can add a packed format later.
100157
static ARRAY_FORMAT_VERSION: u8 = 1u8;

0 commit comments

Comments
 (0)