Skip to content

Commit 14474c1

Browse files
committed
Split into multiple files.
1 parent c97edbf commit 14474c1

File tree

3 files changed

+341
-343
lines changed

3 files changed

+341
-343
lines changed

src/StaticArraysCore.jl

Lines changed: 2 additions & 343 deletions
Original file line numberDiff line numberDiff line change
@@ -40,348 +40,7 @@ const StaticVector{N, T} = StaticArray{Tuple{N}, T, 1}
4040
const StaticMatrix{N, M, T} = StaticArray{Tuple{N, M}, T, 2}
4141
const StaticVecOrMat{T} = Union{StaticVector{<:Any, T}, StaticMatrix{<:Any, <:Any, T}}
4242

43-
# The ::Tuple variants exist to make sure that anything that calls with a tuple
44-
# instead of a Tuple gets through to the constructor, so the user gets a nice
45-
# error message
46-
Base.@pure tuple_length(T::Type{<:Tuple}) = length(T.parameters)
47-
Base.@pure tuple_length(T::Tuple) = length(T)
48-
Base.@pure tuple_prod(T::Type{<:Tuple}) = length(T.parameters) == 0 ? 1 : *(T.parameters...)
49-
Base.@pure tuple_prod(T::Tuple) = prod(T)
50-
Base.@pure tuple_minimum(T::Type{<:Tuple}) = length(T.parameters) == 0 ? 0 : minimum(tuple(T.parameters...))
51-
Base.@pure tuple_minimum(T::Tuple) = minimum(T)
52-
53-
"""
54-
size_to_tuple(::Type{S}) where S<:Tuple
55-
56-
Converts a size given by `Tuple{N, M, ...}` into a tuple `(N, M, ...)`.
57-
"""
58-
Base.@pure function size_to_tuple(::Type{S}) where S<:Tuple
59-
return tuple(S.parameters...)
60-
end
61-
62-
# Something doesn't match up type wise
63-
@generated function check_array_parameters(::Type{Size}, ::Type{T}, ::Type{Val{N}}, ::Type{Val{L}}) where {Size,T,N,L}
64-
if !all(x->isa(x, Int), Size.parameters)
65-
return :(throw(ArgumentError("Static Array parameter Size must be a tuple of Ints (e.g. `SArray{Tuple{3,3}}` or `SMatrix{3,3}`).")))
66-
end
67-
68-
if L != tuple_prod(Size) || L < 0 || tuple_minimum(Size) < 0 || tuple_length(Size) != N
69-
return :(throw(ArgumentError("Size mismatch in Static Array parameters. Got size $Size, dimension $N and length $L.")))
70-
end
71-
72-
return nothing
73-
end
74-
75-
# Cast any Tuple to an TupleN{T}
76-
@generated function convert_ntuple(::Type{T}, d::NTuple{N,Any}) where {N,T}
77-
exprs = ntuple(i -> :(convert(T, d[$i])), Val(N))
78-
return quote
79-
Base.@_inline_meta
80-
$(Expr(:tuple, exprs...))
81-
end
82-
end
83-
84-
85-
"""
86-
SArray{S, T, N, L}(x::NTuple{L})
87-
SArray{S, T, N, L}(x1, x2, x3, ...)
88-
89-
Construct a statically-sized array `SArray`. Since this type is immutable, the data must be
90-
provided upon construction and cannot be mutated later. The `S` parameter is a Tuple-type
91-
specifying the dimensions, or size, of the array - such as `Tuple{3,4,5}` for a 3×4×5-sized
92-
array. The `N` parameter is the dimension of the array; the `L` parameter is the `length`
93-
of the array and is always equal to `prod(S)`. Constructors may drop the `L`, `N` and `T`
94-
parameters if they are inferrable from the input (e.g. `L` is always inferrable from `S`).
95-
96-
SArray{S}(a::Array)
97-
98-
Construct a statically-sized array of dimensions `S` (expressed as a `Tuple{...}`) using
99-
the data from `a`. The `S` parameter is mandatory since the size of `a` is unknown to the
100-
compiler (the element type may optionally also be specified).
101-
"""
102-
struct SArray{S <: Tuple, T, N, L} <: StaticArray{S, T, N}
103-
data::NTuple{L,T}
104-
105-
function SArray{S, T, N, L}(x::NTuple{L,T}) where {S<:Tuple, T, N, L}
106-
check_array_parameters(S, T, Val{N}, Val{L})
107-
new{S, T, N, L}(x)
108-
end
109-
110-
function SArray{S, T, N, L}(x::NTuple{L,Any}) where {S<:Tuple, T, N, L}
111-
check_array_parameters(S, T, Val{N}, Val{L})
112-
new{S, T, N, L}(convert_ntuple(T, x))
113-
end
114-
end
115-
116-
@inline SArray{S,T,N}(x::Tuple) where {S<:Tuple,T,N} = SArray{S,T,N,tuple_prod(S)}(x)
117-
118-
"""
119-
SVector{S, T}(x::NTuple{S, T})
120-
SVector{S, T}(x1, x2, x3, ...)
121-
122-
Construct a statically-sized vector `SVector`. Since this type is immutable,
123-
the data must be provided upon construction and cannot be mutated later.
124-
Constructors may drop the `T` and `S` parameters if they are inferrable from the
125-
input (e.g. `SVector(1,2,3)` constructs an `SVector{3, Int}`).
126-
127-
SVector{S}(vec::Vector)
128-
129-
Construct a statically-sized vector of length `S` using the data from `vec`.
130-
The parameter `S` is mandatory since the length of `vec` is unknown to the
131-
compiler (the element type may optionally also be specified).
132-
"""
133-
const SVector{S, T} = SArray{Tuple{S}, T, 1, S}
134-
135-
"""
136-
SMatrix{S1, S2, T, L}(x::NTuple{L, T})
137-
SMatrix{S1, S2, T, L}(x1, x2, x3, ...)
138-
139-
Construct a statically-sized matrix `SMatrix`. Since this type is immutable,
140-
the data must be provided upon construction and cannot be mutated later. The
141-
`L` parameter is the `length` of the array and is always equal to `S1 * S2`.
142-
Constructors may drop the `L`, `T` and even `S2` parameters if they are inferrable
143-
from the input (e.g. `L` is always inferrable from `S1` and `S2`).
144-
145-
SMatrix{S1, S2}(mat::Matrix)
146-
147-
Construct a statically-sized matrix of dimensions `S1 × S2` using the data from
148-
`mat`. The parameters `S1` and `S2` are mandatory since the size of `mat` is
149-
unknown to the compiler (the element type may optionally also be specified).
150-
"""
151-
const SMatrix{S1, S2, T, L} = SArray{Tuple{S1, S2}, T, 2, L}
152-
153-
# MArray
154-
155-
"""
156-
MArray{S, T, N, L}(undef)
157-
MArray{S, T, N, L}(x::NTuple{L})
158-
MArray{S, T, N, L}(x1, x2, x3, ...)
159-
160-
161-
Construct a statically-sized, mutable array `MArray`. The data may optionally be
162-
provided upon construction and can be mutated later. The `S` parameter is a Tuple-type
163-
specifying the dimensions, or size, of the array - such as `Tuple{3,4,5}` for a 3×4×5-sized
164-
array. The `N` parameter is the dimension of the array; the `L` parameter is the `length`
165-
of the array and is always equal to `prod(S)`. Constructors may drop the `L`, `N` and `T`
166-
parameters if they are inferrable from the input (e.g. `L` is always inferrable from `S`).
167-
168-
MArray{S}(a::Array)
169-
170-
Construct a statically-sized, mutable array of dimensions `S` (expressed as a `Tuple{...}`)
171-
using the data from `a`. The `S` parameter is mandatory since the size of `a` is unknown to
172-
the compiler (the element type may optionally also be specified).
173-
"""
174-
mutable struct MArray{S <: Tuple, T, N, L} <: StaticArray{S, T, N}
175-
data::NTuple{L,T}
176-
177-
function MArray{S,T,N,L}(x::NTuple{L,T}) where {S<:Tuple,T,N,L}
178-
check_array_parameters(S, T, Val{N}, Val{L})
179-
new{S,T,N,L}(x)
180-
end
181-
182-
function MArray{S,T,N,L}(x::NTuple{L,Any}) where {S<:Tuple,T,N,L}
183-
check_array_parameters(S, T, Val{N}, Val{L})
184-
new{S,T,N,L}(convert_ntuple(T, x))
185-
end
186-
187-
function MArray{S,T,N,L}(::UndefInitializer) where {S<:Tuple,T,N,L}
188-
check_array_parameters(S, T, Val{N}, Val{L})
189-
new{S,T,N,L}()
190-
end
191-
end
192-
193-
@inline MArray{S,T,N}(x::Tuple) where {S<:Tuple,T,N} = MArray{S,T,N,tuple_prod(S)}(x)
194-
195-
"""
196-
MVector{S,T}(undef)
197-
MVector{S,T}(x::NTuple{S, T})
198-
MVector{S,T}(x1, x2, x3, ...)
199-
200-
Construct a statically-sized, mutable vector `MVector`. Data may optionally be
201-
provided upon construction, and can be mutated later. Constructors may drop the
202-
`T` and `S` parameters if they are inferrable from the input (e.g.
203-
`MVector(1,2,3)` constructs an `MVector{3, Int}`).
204-
205-
MVector{S}(vec::Vector)
206-
207-
Construct a statically-sized, mutable vector of length `S` using the data from
208-
`vec`. The parameter `S` is mandatory since the length of `vec` is unknown to the
209-
compiler (the element type may optionally also be specified).
210-
"""
211-
const MVector{S, T} = MArray{Tuple{S}, T, 1, S}
212-
213-
"""
214-
MMatrix{S1, S2, T, L}(undef)
215-
MMatrix{S1, S2, T, L}(x::NTuple{L, T})
216-
MMatrix{S1, S2, T, L}(x1, x2, x3, ...)
217-
218-
Construct a statically-sized, mutable matrix `MMatrix`. The data may optionally
219-
be provided upon construction and can be mutated later. The `L` parameter is the
220-
`length` of the array and is always equal to `S1 * S2`. Constructors may drop
221-
the `L`, `T` and even `S2` parameters if they are inferrable from the input
222-
(e.g. `L` is always inferrable from `S1` and `S2`).
223-
224-
MMatrix{S1, S2}(mat::Matrix)
225-
226-
Construct a statically-sized, mutable matrix of dimensions `S1 × S2` using the data from
227-
`mat`. The parameters `S1` and `S2` are mandatory since the size of `mat` is
228-
unknown to the compiler (the element type may optionally also be specified).
229-
"""
230-
const MMatrix{S1, S2, T, L} = MArray{Tuple{S1, S2}, T, 2, L}
231-
232-
233-
# SizedArray
234-
235-
require_one_based_indexing(A...) = !Base.has_offset_axes(A...) ||
236-
throw(ArgumentError("offset arrays are not supported but got an array with index other than 1"))
237-
238-
"""
239-
SizedArray{Tuple{dims...}}(array)
240-
241-
Wraps an `AbstractArray` with a static size, so to take advantage of the (faster)
242-
methods defined by the static array package. The size is checked once upon
243-
construction to determine if the number of elements (`length`) match, but the
244-
array may be reshaped.
245-
246-
The aliases `SizedVector{N}` and `SizedMatrix{N,M}` are provided as more
247-
convenient names for one and two dimensional `SizedArray`s. For example, to
248-
wrap a 2x3 array `a` in a `SizedArray`, use `SizedMatrix{2,3}(a)`.
249-
"""
250-
struct SizedArray{S<:Tuple,T,N,M,TData<:AbstractArray{T,M}} <: StaticArray{S,T,N}
251-
data::TData
252-
253-
function SizedArray{S,T,N,M,TData}(a::TData) where {S<:Tuple,T,N,M,TData<:AbstractArray{T,M}}
254-
require_one_based_indexing(a)
255-
if size(a) != size_to_tuple(S) && size(a) != (tuple_prod(S),)
256-
throw(DimensionMismatch("Dimensions $(size(a)) don't match static size $S"))
257-
end
258-
return new{S,T,N,M,TData}(a)
259-
end
260-
261-
function SizedArray{S,T,N,1,TData}(::UndefInitializer) where {S<:Tuple,T,N,TData<:AbstractArray{T,1}}
262-
return new{S,T,N,1,TData}(TData(undef, tuple_prod(S)))
263-
end
264-
function SizedArray{S,T,N,N,TData}(::UndefInitializer) where {S<:Tuple,T,N,TData<:AbstractArray{T,N}}
265-
return new{S,T,N,N,TData}(TData(undef, size_to_tuple(S)...))
266-
end
267-
end
268-
269-
const SizedVector{S,T} = SizedArray{Tuple{S},T,1,1}
270-
271-
const SizedMatrix{S1,S2,T} = SizedArray{Tuple{S1,S2},T,2}
272-
273-
# FieldArray
274-
275-
"""
276-
abstract FieldArray{N, T, D} <: StaticArray{N, T, D}
277-
278-
Inheriting from this type will make it easy to create your own rank-D tensor types. A `FieldArray`
279-
will automatically define `getindex` and `setindex!` appropriately. An immutable
280-
`FieldArray` will be as performant as an `SArray` of similar length and element type,
281-
while a mutable `FieldArray` will behave similarly to an `MArray`.
282-
283-
Note that you must define the fields of any `FieldArray` subtype in column major order. If you
284-
want to use an alternative ordering you will need to pay special attention in providing your
285-
own definitions of `getindex`, `setindex!` and tuple conversion.
286-
287-
If you define a `FieldArray` which is parametric on the element type you should
288-
consider defining `similar_type` as in the `FieldVector` example.
289-
290-
291-
# Example
292-
293-
struct Stiffness <: FieldArray{Tuple{2,2,2,2}, Float64, 4}
294-
xxxx::Float64
295-
yxxx::Float64
296-
xyxx::Float64
297-
yyxx::Float64
298-
xxyx::Float64
299-
yxyx::Float64
300-
xyyx::Float64
301-
yyyx::Float64
302-
xxxy::Float64
303-
yxxy::Float64
304-
xyxy::Float64
305-
yyxy::Float64
306-
xxyy::Float64
307-
yxyy::Float64
308-
xyyy::Float64
309-
yyyy::Float64
310-
end
311-
"""
312-
abstract type FieldArray{N, T, D} <: StaticArray{N, T, D} end
313-
314-
"""
315-
abstract FieldMatrix{N1, N2, T} <: FieldArray{Tuple{N1, N2}, 2}
316-
317-
Inheriting from this type will make it easy to create your own rank-two tensor types. A `FieldMatrix`
318-
will automatically define `getindex` and `setindex!` appropriately. An immutable
319-
`FieldMatrix` will be as performant as an `SMatrix` of similar length and element type,
320-
while a mutable `FieldMatrix` will behave similarly to an `MMatrix`.
321-
322-
Note that the fields of any subtype of `FieldMatrix` must be defined in column
323-
major order unless you are willing to implement your own `getindex`.
324-
325-
If you define a `FieldMatrix` which is parametric on the element type you
326-
should consider defining `similar_type` as in the `FieldVector` example.
327-
328-
# Example
329-
330-
struct Stress <: FieldMatrix{3, 3, Float64}
331-
xx::Float64
332-
yx::Float64
333-
zx::Float64
334-
xy::Float64
335-
yy::Float64
336-
zy::Float64
337-
xz::Float64
338-
yz::Float64
339-
zz::Float64
340-
end
341-
342-
Note that the fields of any subtype of `FieldMatrix` must be defined in column major order.
343-
This means that formatting of constructors for literal `FieldMatrix` can be confusing. For example
344-
345-
sigma = Stress(1.0, 2.0, 3.0,
346-
4.0, 5.0, 6.0,
347-
7.0, 8.0, 9.0)
348-
349-
3×3 Stress:
350-
1.0 4.0 7.0
351-
2.0 5.0 8.0
352-
3.0 6.0 9.0
353-
354-
will give you the transpose of what the multi-argument formatting suggests. For clarity,
355-
you may consider using the alternative
356-
357-
sigma = Stress(SA[1.0 2.0 3.0;
358-
4.0 5.0 6.0;
359-
7.0 8.0 9.0])
360-
"""
361-
abstract type FieldMatrix{N1, N2, T} <: FieldArray{Tuple{N1, N2}, T, 2} end
362-
363-
"""
364-
abstract FieldVector{N, T} <: FieldArray{Tuple{N}, 1}
365-
366-
Inheriting from this type will make it easy to create your own vector types. A `FieldVector`
367-
will automatically define `getindex` and `setindex!` appropriately. An immutable
368-
`FieldVector` will be as performant as an `SVector` of similar length and element type,
369-
while a mutable `FieldVector` will behave similarly to an `MVector`.
370-
371-
If you define a `FieldVector` which is parametric on the element type you
372-
should consider defining `similar_type` to preserve your array type through
373-
array operations as in the example below.
374-
375-
# Example
376-
377-
struct Vec3D{T} <: FieldVector{3, T}
378-
x::T
379-
y::T
380-
z::T
381-
end
382-
383-
StaticArrays.similar_type(::Type{<:Vec3D}, ::Type{T}, s::Size{(3,)}) where {T} = Vec3D{T}
384-
"""
385-
abstract type FieldVector{N, T} <: FieldArray{Tuple{N}, T, 1} end
43+
include("staticarrays.jl")
44+
include("utils.jl")
38645

38746
end # module

0 commit comments

Comments
 (0)