Skip to content

Commit 2d42a16

Browse files
committed
Add toArraySlice and unsafeFromArraySlice functions
1 parent 2ec9d87 commit 2d42a16

File tree

3 files changed

+52
-5
lines changed

3 files changed

+52
-5
lines changed

vector/changelog.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,8 @@
4747
* Add `groupBy` and `group` for `Data.Vector.Generic` and the specialized
4848
version in `Data.Vector`, `Data.Vector.Unboxed`, `Data.Vector.Storable` and
4949
`Data.Vector.Primitive`.
50+
* Add `toArraySlice` and `unsafeFromArraySlice` functions for conversion to and
51+
from the underlying boxed `Array`.
5052

5153
# Changes in version 0.12.3.1
5254

vector/src/Data/Vector.hs

Lines changed: 32 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -163,7 +163,7 @@ module Data.Vector (
163163
toList, Data.Vector.fromList, Data.Vector.fromListN,
164164

165165
-- ** Arrays
166-
fromArray, toArray,
166+
toArray, fromArray, toArraySlice, unsafeFromArraySlice,
167167

168168
-- ** Other vector types
169169
G.convert,
@@ -2136,16 +2136,43 @@ fromListN = G.fromListN
21362136
-- @since 0.12.2.0
21372137
fromArray :: Array a -> Vector a
21382138
{-# INLINE fromArray #-}
2139-
fromArray x = Vector 0 (sizeofArray x) x
2139+
fromArray arr = Vector 0 (sizeofArray arr) arr
21402140

21412141
-- | /O(n)/ Convert a vector to an array.
21422142
--
21432143
-- @since 0.12.2.0
21442144
toArray :: Vector a -> Array a
21452145
{-# INLINE toArray #-}
2146-
toArray (Vector offset size arr)
2147-
| offset == 0 && size == sizeofArray arr = arr
2148-
| otherwise = cloneArray arr offset size
2146+
toArray (Vector offset len arr)
2147+
| offset == 0 && len == sizeofArray arr = arr
2148+
| otherwise = cloneArray arr offset len
2149+
2150+
-- | /O(1)/ Extract the underlying `Array`, offset where vector starts and the
2151+
-- total number of elements in the vector. Below property always holds:
2152+
--
2153+
-- > let (array, offset, len) = toArraySlice v
2154+
-- > v === unsafeFromArraySlice len offset array
2155+
--
2156+
-- @since 0.13.0.0
2157+
toArraySlice :: Vector a -> (Array a, Int, Int)
2158+
{-# INLINE toArraySlice #-}
2159+
toArraySlice (Vector offset len arr) = (arr, offset, len)
2160+
2161+
2162+
-- | /O(1)/ Convert an array slice to a vector. This function is very unsafe,
2163+
-- because constructing an invalid vector can yield almost all other safe
2164+
-- functions in this module unsafe. These are equivalent:
2165+
--
2166+
-- > unsafeFromArraySlice len offset === unsafeTake len . unsafeDrop offset . fromArray
2167+
--
2168+
-- @since 0.13.0.0
2169+
unsafeFromArraySlice ::
2170+
Array a -- ^ Immutable boxed array.
2171+
-> Int -- ^ Offset
2172+
-> Int -- ^ Length
2173+
-> Vector a
2174+
{-# INLINE unsafeFromArraySlice #-}
2175+
unsafeFromArraySlice arr offset len = Vector offset len arr
21492176

21502177
-- Conversions - Mutable vectors
21512178
-- -----------------------------

vector/tests/Tests/Vector/UnitTests.hs

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -91,6 +91,8 @@ tests =
9191
, testGroup "Data.Vector"
9292
[ testCase "MonadFix" checkMonadFix
9393
, testCase "toFromArray" toFromArray
94+
, testCase "toFromArraySlice" toFromArraySlice
95+
, testCase "toFromArraySliceUnsafe" toFromArraySliceUnsafe
9496
, testCase "toFromMutableArray" toFromMutableArray
9597
]
9698
]
@@ -202,6 +204,22 @@ toFromArray =
202204
mkArrayRoundtrip $ \name v ->
203205
assertEqual name v $ Boxed.fromArray (Boxed.toArray v)
204206

207+
toFromArraySlice :: Assertion
208+
toFromArraySlice =
209+
mkArrayRoundtrip $ \name v ->
210+
case Boxed.toArraySlice v of
211+
(arr, off, n) ->
212+
assertEqual name v $
213+
Boxed.take n (Boxed.drop off (Boxed.fromArray arr))
214+
215+
toFromArraySliceUnsafe :: Assertion
216+
toFromArraySliceUnsafe =
217+
mkArrayRoundtrip $ \name v ->
218+
case Boxed.toArraySlice v of
219+
(arr, off, n) ->
220+
assertEqual name v $
221+
Boxed.unsafeFromArraySlice arr off n
222+
205223
toFromMutableArray :: Assertion
206224
toFromMutableArray = mkArrayRoundtrip assetRoundtrip
207225
where

0 commit comments

Comments
 (0)