{-# LANGUAGE ExistentialQuantification #-}
{-# LANGUAGE ExplicitNamespaces #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE GADTs #-}
{-# LANGUAGE InstanceSigs #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE TypeApplications #-}

module DataFrame.Internal.Row where

import qualified Data.List as L
import qualified Data.Map as M
import qualified Data.Text as T
import qualified Data.Vector as V
import qualified Data.Vector.Unboxed as VU

import Control.Exception (throw)
import Data.Function (on)
import Data.Maybe (catMaybes, fromMaybe, isNothing)
import Data.Type.Equality (TestEquality (..))
import Data.Typeable (Typeable, type (:~:) (..))
import DataFrame.Errors (DataFrameException (..), TypeErrorContext (..))
import DataFrame.Internal.Column
import DataFrame.Internal.DataFrame
import DataFrame.Internal.Expression (Expr (..))
import DataFrame.Internal.PackedText (packedIndexText, packedLength)
import Type.Reflection (TypeRep, typeOf, typeRep)

data Any where
    Value :: (Columnable a) => a -> Any
    -- Saves us the extra indirection we get from making Value (Maybe a)
    -- and having to unpack it again to check for nulls.
    -- Instead, we just have Null as a separate constructor.
    Null :: Any

instance Eq Any where
    (==) :: Any -> Any -> Bool
    (Value a
a) == :: Any -> Any -> Bool
== (Value a
b) = Bool -> Maybe Bool -> Bool
forall a. a -> Maybe a -> a
fromMaybe Bool
False (Maybe Bool -> Bool) -> Maybe Bool -> Bool
forall a b. (a -> b) -> a -> b
$ do
        a :~: a
Refl <- TypeRep a -> TypeRep a -> Maybe (a :~: a)
forall a b. TypeRep a -> TypeRep b -> Maybe (a :~: b)
forall {k} (f :: k -> *) (a :: k) (b :: k).
TestEquality f =>
f a -> f b -> Maybe (a :~: b)
testEquality (a -> TypeRep a
forall a. Typeable a => a -> TypeRep a
typeOf a
a) (a -> TypeRep a
forall a. Typeable a => a -> TypeRep a
typeOf a
b)
        Bool -> Maybe Bool
forall a. a -> Maybe a
forall (m :: * -> *) a. Monad m => a -> m a
return (Bool -> Maybe Bool) -> Bool -> Maybe Bool
forall a b. (a -> b) -> a -> b
$ a
a a -> a -> Bool
forall a. Eq a => a -> a -> Bool
== a
a
b
    Any
Null == Any
Null = Bool
True
    Any
_ == Any
_ = Bool
False

instance Show Any where
    show :: Any -> String
    show :: Any -> [Char]
show (Value a
a) = Text -> [Char]
T.unpack (a -> Text
forall a. Columnable a => a -> Text
showValue a
a)
    show Any
Null = [Char]
"null"

showValue :: forall a. (Columnable a) => a -> T.Text
showValue :: forall a. Columnable a => a -> Text
showValue a
v = case TypeRep a -> TypeRep Text -> Maybe (a :~: Text)
forall a b. TypeRep a -> TypeRep b -> Maybe (a :~: b)
forall {k} (f :: k -> *) (a :: k) (b :: k).
TestEquality f =>
f a -> f b -> Maybe (a :~: b)
testEquality (forall a. Typeable a => TypeRep a
forall {k} (a :: k). Typeable a => TypeRep a
typeRep @a) (forall a. Typeable a => TypeRep a
forall {k} (a :: k). Typeable a => TypeRep a
typeRep @T.Text) of
    Just a :~: Text
Refl -> a
Text
v
    Maybe (a :~: Text)
Nothing -> case TypeRep a -> TypeRep [Char] -> Maybe (a :~: [Char])
forall a b. TypeRep a -> TypeRep b -> Maybe (a :~: b)
forall {k} (f :: k -> *) (a :: k) (b :: k).
TestEquality f =>
f a -> f b -> Maybe (a :~: b)
testEquality (forall a. Typeable a => TypeRep a
forall {k} (a :: k). Typeable a => TypeRep a
typeRep @a) (forall a. Typeable a => TypeRep a
forall {k} (a :: k). Typeable a => TypeRep a
typeRep @String) of
        Just a :~: [Char]
Refl -> [Char] -> Text
T.pack a
[Char]
v
        Maybe (a :~: [Char])
Nothing -> ([Char] -> Text
T.pack ([Char] -> Text) -> (a -> [Char]) -> a -> Text
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> [Char]
forall a. Show a => a -> [Char]
show) a
v

-- | Wraps a value into an \Any\ type. This helps up represent rows as heterogenous lists.
toAny :: forall a. (Columnable a) => a -> Any
toAny :: forall a. Columnable a => a -> Any
toAny = a -> Any
forall a. Columnable a => a -> Any
Value

-- | Unwraps a value from an \Any\ type. A 'Null' cell yields 'Nothing'.
fromAny :: forall a. (Columnable a) => Any -> Maybe a
fromAny :: forall a. Columnable a => Any -> Maybe a
fromAny Any
Null = Maybe a
forall a. Maybe a
Nothing
fromAny (Value (a
v :: b)) = do
    a :~: a
Refl <- TypeRep a -> TypeRep a -> Maybe (a :~: a)
forall a b. TypeRep a -> TypeRep b -> Maybe (a :~: b)
forall {k} (f :: k -> *) (a :: k) (b :: k).
TestEquality f =>
f a -> f b -> Maybe (a :~: b)
testEquality (forall a. Typeable a => TypeRep a
forall {k} (a :: k). Typeable a => TypeRep a
typeRep @a) (forall a. Typeable a => TypeRep a
forall {k} (a :: k). Typeable a => TypeRep a
typeRep @b)
    a -> Maybe a
forall a. a -> Maybe a
forall (f :: * -> *) a. Applicative f => a -> f a
pure a
a
v

{- | Wrap a column cell into an 'Any', honouring the column's null bitmap: a slot
marked invalid becomes 'Null', any other slot becomes a 'Value'. Only needs
@Columnable a@ (the stored element type), not @Columnable (Maybe a)@.
-}
cellAny :: (Columnable a) => Maybe Bitmap -> Int -> a -> Any
cellAny :: forall a. Columnable a => Maybe Bitmap -> Int -> a -> Any
cellAny Maybe Bitmap
Nothing Int
_ a
x = a -> Any
forall a. Columnable a => a -> Any
Value a
x
cellAny (Just Bitmap
bm) Int
i a
x = if Bitmap -> Int -> Bool
bitmapTestBit Bitmap
bm Int
i then a -> Any
forall a. Columnable a => a -> Any
Value a
x else Any
Null

type Row = V.Vector Any

(!?) :: [a] -> Int -> Maybe a
!? :: forall a. [a] -> Int -> Maybe a
(!?) [] Int
_ = Maybe a
forall a. Maybe a
Nothing
(!?) (a
x : [a]
_) Int
0 = a -> Maybe a
forall a. a -> Maybe a
Just a
x
(!?) (a
_x : [a]
xs) Int
n = [a] -> Int -> Maybe a
forall a. [a] -> Int -> Maybe a
(!?) [a]
xs (Int
n Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
1)

mkColumnFromRow :: T.Text -> Int -> [[Any]] -> Column
mkColumnFromRow :: Text -> Int -> [[Any]] -> Column
mkColumnFromRow Text
name Int
i [[Any]]
rows =
    case (Any -> Bool) -> [Any] -> Maybe Any
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Maybe a
L.find Any -> Bool
isValue [Any]
cells of
        Just (Value (a
_ :: a)) ->
            let collect :: Int -> Any -> Maybe a
collect Int
_ Any
Null = Maybe a
forall a. Maybe a
Nothing :: Maybe a
                collect Int
r (Value (a
v' :: b)) =
                    case TypeRep a -> TypeRep a -> Maybe (a :~: a)
forall a b. TypeRep a -> TypeRep b -> Maybe (a :~: b)
forall {k} (f :: k -> *) (a :: k) (b :: k).
TestEquality f =>
f a -> f b -> Maybe (a :~: b)
testEquality (forall a. Typeable a => TypeRep a
forall {k} (a :: k). Typeable a => TypeRep a
typeRep @a) (forall a. Typeable a => TypeRep a
forall {k} (a :: k). Typeable a => TypeRep a
typeRep @b) of
                        Just a :~: a
Refl -> a -> Maybe a
forall a. a -> Maybe a
Just a
a
v'
                        Maybe (a :~: a)
Nothing -> DataFrameException -> Maybe a
forall a e. Exception e => e -> a
throw (Int -> TypeRep a -> TypeRep a -> DataFrameException
forall x y.
(Typeable x, Typeable y) =>
Int -> TypeRep x -> TypeRep y -> DataFrameException
mismatchAt Int
r (forall a. Typeable a => TypeRep a
forall {k} (a :: k). Typeable a => TypeRep a
typeRep @b) (forall a. Typeable a => TypeRep a
forall {k} (a :: k). Typeable a => TypeRep a
typeRep @a))
                maybes :: [Maybe a]
maybes = (Int -> Any -> Maybe a) -> [Int] -> [Any] -> [Maybe a]
forall a b c. (a -> b -> c) -> [a] -> [b] -> [c]
zipWith Int -> Any -> Maybe a
collect [Int
0 :: Int ..] [Any]
cells
             in if (Maybe a -> Bool) -> [Maybe a] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
any Maybe a -> Bool
forall a. Maybe a -> Bool
isNothing [Maybe a]
maybes
                    then Vector (Maybe a) -> Column
forall a. Columnable a => Vector (Maybe a) -> Column
fromMaybeVec ([Maybe a] -> Vector (Maybe a)
forall a. [a] -> Vector a
V.fromList [Maybe a]
maybes)
                    else [a] -> Column
forall a.
(Columnable a, ColumnifyRep (KindOf a) a) =>
[a] -> Column
fromList ([Maybe a] -> [a]
forall a. [Maybe a] -> [a]
catMaybes [Maybe a]
maybes)
        Maybe Any
_ -> Vector (Maybe Text) -> Column
forall a. Columnable a => Vector (Maybe a) -> Column
fromMaybeVec ([Maybe Text] -> Vector (Maybe Text)
forall a. [a] -> Vector a
V.fromList ((Any -> Maybe Text) -> [Any] -> [Maybe Text]
forall a b. (a -> b) -> [a] -> [b]
map (Maybe Text -> Any -> Maybe Text
forall a b. a -> b -> a
const (Maybe Text
forall a. Maybe a
Nothing :: Maybe T.Text)) [Any]
cells))
  where
    cells :: [Any]
cells = (Int -> [Any] -> Any) -> [Int] -> [[Any]] -> [Any]
forall a b c. (a -> b -> c) -> [a] -> [b] -> [c]
zipWith Int -> [Any] -> Any
cellAt [Int
0 :: Int ..] [[Any]]
rows
    cellAt :: Int -> [Any] -> Any
cellAt Int
r [Any]
row = Any -> Maybe Any -> Any
forall a. a -> Maybe a -> a
fromMaybe (DataFrameException -> Any
forall a e. Exception e => e -> a
throw (Int -> DataFrameException
missingCellAt Int
r)) ([Any]
row [Any] -> Int -> Maybe Any
forall a. [a] -> Int -> Maybe a
!? Int
i)
    isValue :: Any -> Bool
isValue (Value a
_) = Bool
True
    isValue Any
Null = Bool
False
    mismatchAt ::
        forall x y.
        (Typeable x, Typeable y) => Int -> TypeRep x -> TypeRep y -> DataFrameException
    mismatchAt :: forall x y.
(Typeable x, Typeable y) =>
Int -> TypeRep x -> TypeRep y -> DataFrameException
mismatchAt Int
r TypeRep x
actual TypeRep y
expected =
        TypeErrorContext x y -> DataFrameException
forall a b.
(Typeable a, Typeable b) =>
TypeErrorContext a b -> DataFrameException
TypeMismatchException
            MkTypeErrorContext
                { userType :: Either [Char] (TypeRep x)
userType = TypeRep x -> Either [Char] (TypeRep x)
forall a b. b -> Either a b
Right TypeRep x
actual
                , expectedType :: Either [Char] (TypeRep y)
expectedType = TypeRep y -> Either [Char] (TypeRep y)
forall a b. b -> Either a b
Right TypeRep y
expected
                , errorColumnName :: Maybe [Char]
errorColumnName = [Char] -> Maybe [Char]
forall a. a -> Maybe a
Just (Text -> [Char]
T.unpack Text
name [Char] -> ShowS
forall a. [a] -> [a] -> [a]
++ [Char]
", row " [Char] -> ShowS
forall a. [a] -> [a] -> [a]
++ Int -> [Char]
forall a. Show a => a -> [Char]
show Int
r)
                , callingFunctionName :: Maybe [Char]
callingFunctionName = [Char] -> Maybe [Char]
forall a. a -> Maybe a
Just [Char]
"fromRows"
                }
    missingCellAt :: Int -> DataFrameException
missingCellAt Int
r =
        Text -> DataFrameException
InternalException
            ( Text
"fromRows: row "
                Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> [Char] -> Text
T.pack (Int -> [Char]
forall a. Show a => a -> [Char]
show Int
r)
                Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
" has no cell for column "
                Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
name
            )

{- | Convert the whole dataframe to a list of rows, one per row index in natural
order; each row lists all columns ordered by column index. Materializes every
row, so prefer 'toRowVector' for large frames.

>>> toRowList df
[[("name", "Alice"), ("age", 25), ...], [("name", "Bob"), ("age", 30), ...], ...]
-}
toRowList :: DataFrame -> [[(T.Text, Any)]]
toRowList :: DataFrame -> [[(Text, Any)]]
toRowList DataFrame
df =
    let
        names :: [Text]
names = ((Text, Int) -> Text) -> [(Text, Int)] -> [Text]
forall a b. (a -> b) -> [a] -> [b]
map (Text, Int) -> Text
forall a b. (a, b) -> a
fst (((Text, Int) -> (Text, Int) -> Ordering)
-> [(Text, Int)] -> [(Text, Int)]
forall a. (a -> a -> Ordering) -> [a] -> [a]
L.sortBy (Int -> Int -> Ordering
forall a. Ord a => a -> a -> Ordering
compare (Int -> Int -> Ordering)
-> ((Text, Int) -> Int) -> (Text, Int) -> (Text, Int) -> Ordering
forall b c a. (b -> b -> c) -> (a -> b) -> a -> a -> c
`on` (Text, Int) -> Int
forall a b. (a, b) -> b
snd) ([(Text, Int)] -> [(Text, Int)]) -> [(Text, Int)] -> [(Text, Int)]
forall a b. (a -> b) -> a -> b
$ Map Text Int -> [(Text, Int)]
forall k a. Map k a -> [(k, a)]
M.toList (DataFrame -> Map Text Int
columnIndices DataFrame
df))
     in
        (Int -> [(Text, Any)]) -> [Int] -> [[(Text, Any)]]
forall a b. (a -> b) -> [a] -> [b]
map
            ([Text] -> [Any] -> [(Text, Any)]
forall a b. [a] -> [b] -> [(a, b)]
zip [Text]
names ([Any] -> [(Text, Any)]) -> (Int -> [Any]) -> Int -> [(Text, Any)]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Vector Any -> [Any]
forall a. Vector a -> [a]
V.toList (Vector Any -> [Any]) -> (Int -> Vector Any) -> Int -> [Any]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. DataFrame -> [Text] -> Int -> Vector Any
mkRowRep DataFrame
df [Text]
names)
            [Int
0 .. ((Int, Int) -> Int
forall a b. (a, b) -> a
fst (DataFrame -> (Int, Int)
dataframeDimensions DataFrame
df) Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
1)]

{- | Convert the dataframe to a vector of rows containing only the named columns,
in the given order. An empty name list yields one empty row per dataframe row.

>>> toRowVector ["name", "age"] df
Vector of rows with only name and age fields
-}
toRowVector :: [T.Text] -> DataFrame -> V.Vector Row
toRowVector :: [Text] -> DataFrame -> Vector (Vector Any)
toRowVector [Text]
names DataFrame
df = Int -> (Int -> Vector Any) -> Vector (Vector Any)
forall a. Int -> (Int -> a) -> Vector a
V.generate ((Int, Int) -> Int
forall a b. (a, b) -> a
fst (DataFrame -> (Int, Int)
dataframeDimensions DataFrame
df)) (DataFrame -> [Text] -> Int -> Vector Any
mkRowRep DataFrame
df [Text]
names)

{- | Given a row gets the value associated with a field.

==== __Examples__

>>> map (rowValue (F.col @Int "age")) (toRowList df)
[25,30, ...]
-}
rowValue :: forall a. Expr a -> [(T.Text, Any)] -> Maybe a
rowValue :: forall a. Expr a -> [(Text, Any)] -> Maybe a
rowValue (Col Text
name) [(Text, Any)]
row = Text -> [(Text, Any)] -> Maybe Any
forall a b. Eq a => a -> [(a, b)] -> Maybe b
lookup Text
name [(Text, Any)]
row Maybe Any -> (Any -> Maybe a) -> Maybe a
forall a b. Maybe a -> (a -> Maybe b) -> Maybe b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= forall a. Columnable a => Any -> Maybe a
fromAny @a
rowValue Expr a
_ [(Text, Any)]
_ = [Char] -> Maybe a
forall a. HasCallStack => [Char] -> a
error [Char]
"Can only get rowValue of column reference"

mkRowFromArgs :: [T.Text] -> DataFrame -> Int -> Row
mkRowFromArgs :: [Text] -> DataFrame -> Int -> Vector Any
mkRowFromArgs [Text]
names DataFrame
df Int
i = (Text -> Any) -> Vector Text -> Vector Any
forall a b. (a -> b) -> Vector a -> Vector b
V.map Text -> Any
get ([Text] -> Vector Text
forall a. [a] -> Vector a
V.fromList [Text]
names)
  where
    get :: Text -> Any
get Text
name = case Text -> DataFrame -> Maybe Column
getColumn Text
name DataFrame
df of
        Maybe Column
Nothing ->
            DataFrameException -> Any
forall a e. Exception e => e -> a
throw (DataFrameException -> Any) -> DataFrameException -> Any
forall a b. (a -> b) -> a -> b
$
                [Text] -> Text -> [Text] -> DataFrameException
ColumnsNotFoundException
                    [Text
name]
                    Text
"[INTERNAL] mkRowFromArgs"
                    (Map Text Int -> [Text]
forall k a. Map k a -> [k]
M.keys (Map Text Int -> [Text]) -> Map Text Int -> [Text]
forall a b. (a -> b) -> a -> b
$ DataFrame -> Map Text Int
columnIndices DataFrame
df)
        Just (BoxedColumn Maybe Bitmap
bm Vector a
column) -> Maybe Bitmap -> Int -> a -> Any
forall a. Columnable a => Maybe Bitmap -> Int -> a -> Any
cellAny Maybe Bitmap
bm Int
i (Vector a
column Vector a -> Int -> a
forall a. Vector a -> Int -> a
V.! Int
i)
        Just (UnboxedColumn Maybe Bitmap
bm Vector a
column) -> Maybe Bitmap -> Int -> a -> Any
forall a. Columnable a => Maybe Bitmap -> Int -> a -> Any
cellAny Maybe Bitmap
bm Int
i (Vector a
column Vector a -> Int -> a
forall a. Unbox a => Vector a -> Int -> a
VU.! Int
i)
        Just (PackedText Maybe Bitmap
bm PackedTextData
p) -> Maybe Bitmap -> Int -> Text -> Any
forall a. Columnable a => Maybe Bitmap -> Int -> a -> Any
cellAny Maybe Bitmap
bm Int
i (PackedTextData -> Int -> Text
packedIndexText PackedTextData
p Int
i)
        Just c :: Column
c@(MergedColumn Column
_ Column
_) ->
            case Column -> Column
materializeMerged (Int -> Int -> Column -> Column
sliceColumn Int
i Int
1 Column
c) of
                BoxedColumn Maybe Bitmap
bm Vector a
column -> Maybe Bitmap -> Int -> a -> Any
forall a. Columnable a => Maybe Bitmap -> Int -> a -> Any
cellAny Maybe Bitmap
bm Int
0 (Vector a
column Vector a -> Int -> a
forall a. Vector a -> Int -> a
V.! Int
0)
                Column
_ -> [Char] -> Any
forall a. HasCallStack => [Char] -> a
error [Char]
"mkRowFromArgs: materializeMerged is boxed"

-- Returns row values in the caller's requested column order, not the
-- dataframe's storage order.
mkRowRep :: DataFrame -> [T.Text] -> Int -> Row
mkRowRep :: DataFrame -> [Text] -> Int -> Vector Any
mkRowRep DataFrame
df [Text]
names Int
i = Int -> (Int -> Any) -> Vector Any
forall a. Int -> (Int -> a) -> Vector a
V.generate ([Text] -> Int
forall a. [a] -> Int
forall (t :: * -> *) a. Foldable t => t a -> Int
L.length [Text]
names) (\Int
index -> Text -> Any
get (Vector Text
names' Vector Text -> Int -> Text
forall a. Vector a -> Int -> a
V.! Int
index))
  where
    names' :: Vector Text
names' = [Text] -> Vector Text
forall a. [a] -> Vector a
V.fromList [Text]
names
    throwError :: Text -> Any
throwError Text
name =
        [Char] -> Any
forall a. HasCallStack => [Char] -> a
error ([Char] -> Any) -> [Char] -> Any
forall a b. (a -> b) -> a -> b
$
            [Char]
"Column "
                [Char] -> ShowS
forall a. [a] -> [a] -> [a]
++ Text -> [Char]
T.unpack Text
name
                [Char] -> ShowS
forall a. [a] -> [a] -> [a]
++ [Char]
" has less items than "
                [Char] -> ShowS
forall a. [a] -> [a] -> [a]
++ [Char]
"the other columns at index "
                [Char] -> ShowS
forall a. [a] -> [a] -> [a]
++ Int -> [Char]
forall a. Show a => a -> [Char]
show Int
i
    get :: Text -> Any
get Text
name = case Text -> DataFrame -> Maybe Column
getColumn Text
name DataFrame
df of
        Just (BoxedColumn Maybe Bitmap
bm Vector a
c) -> case Vector a
c Vector a -> Int -> Maybe a
forall a. Vector a -> Int -> Maybe a
V.!? Int
i of
            Just a
e -> Maybe Bitmap -> Int -> a -> Any
forall a. Columnable a => Maybe Bitmap -> Int -> a -> Any
cellAny Maybe Bitmap
bm Int
i a
e
            Maybe a
Nothing -> Text -> Any
throwError Text
name
        Just (UnboxedColumn Maybe Bitmap
bm Vector a
c) -> case Vector a
c Vector a -> Int -> Maybe a
forall a. Unbox a => Vector a -> Int -> Maybe a
VU.!? Int
i of
            Just a
e -> Maybe Bitmap -> Int -> a -> Any
forall a. Columnable a => Maybe Bitmap -> Int -> a -> Any
cellAny Maybe Bitmap
bm Int
i a
e
            Maybe a
Nothing -> Text -> Any
throwError Text
name
        Just (PackedText Maybe Bitmap
bm PackedTextData
p)
            | Int
i Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
< PackedTextData -> Int
packedLength PackedTextData
p -> Maybe Bitmap -> Int -> Text -> Any
forall a. Columnable a => Maybe Bitmap -> Int -> a -> Any
cellAny Maybe Bitmap
bm Int
i (PackedTextData -> Int -> Text
packedIndexText PackedTextData
p Int
i)
            | Bool
otherwise -> Text -> Any
throwError Text
name
        Just c :: Column
c@(MergedColumn Column
_ Column
_)
            | Int
i Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
< Column -> Int
columnLength Column
c ->
                case Column -> Column
materializeMerged (Int -> Int -> Column -> Column
sliceColumn Int
i Int
1 Column
c) of
                    BoxedColumn Maybe Bitmap
bm Vector a
column -> Maybe Bitmap -> Int -> a -> Any
forall a. Columnable a => Maybe Bitmap -> Int -> a -> Any
cellAny Maybe Bitmap
bm Int
0 (Vector a
column Vector a -> Int -> a
forall a. Vector a -> Int -> a
V.! Int
0)
                    Column
_ -> [Char] -> Any
forall a. HasCallStack => [Char] -> a
error [Char]
"mkRowRep: materializeMerged is boxed"
            | Bool
otherwise -> Text -> Any
throwError Text
name
        Maybe Column
Nothing ->
            DataFrameException -> Any
forall a e. Exception e => e -> a
throw (DataFrameException -> Any) -> DataFrameException -> Any
forall a b. (a -> b) -> a -> b
$ [Text] -> Text -> [Text] -> DataFrameException
ColumnsNotFoundException [Text
name] Text
"mkRowRep" (Map Text Int -> [Text]
forall k a. Map k a -> [k]
M.keys (Map Text Int -> [Text]) -> Map Text Int -> [Text]
forall a b. (a -> b) -> a -> b
$ DataFrame -> Map Text Int
columnIndices DataFrame
df)