Assume I created a type as follows:
data RequestAck =
RequestAck { ackOK :: Word32, ackMsgCode :: Word32 }
I can see that it is 2 * 4 bytes big and make that a constant somewhere.
The only problems is that once I add a field to the type, I'd have to remember to update my constant.
Is there a function out there that will provide me with the size of a given type e.g., t -> Int
?
The function that comes close to what I want is
gsize :: Data a => a -> Int
inside the Data.Generics.Schemes module, but I don't want to have to make my type an instance of Data
.
Is there a more generic solution out there?
To be sure, I'm looking for a function that operates on the static type, e.g., I don't want to pass an instance, but the type itself.
This really depends on how you're turning this into bytes.
As a Word32
, there is no fixed size. What you see as a Word32
could be an unapplied closure taking up hundreds of megabytes of space. Or it could be a simple boxed type (which would be larger than 4 bytes). Or it could be some kind of inline tagged type (in which case it depends on the platform). Or it could be elided (in which case it doesn't exist).
The only time when you can really say what size something like this is is when you convert to binary. If you're doing this to interface with the FFI, you can use the sizeOf
member of Foreign.Storable
. Of course, you need to write a Storable instance for your type if you want to just apply sizeOf
directly to it. If you're serializing via Data.Binary... well, just serialize the thing, really. You usually don't need to know the actual size beforehand (and if you do for a size header, just serialize the body you're counting the size of into a temporary lazy bytestring, then take the size, then write the size and temp bytestring).
bitSizeMaybe
and finiteBitSize
from Data.Bits provide the size in bits. They supersede bitSize
from the same module.
finiteBitSize :: b -> Int
Return the number of bits in the type of the argument. The actual value of the argument is ignored.
finiteBitSize = bitSize
bitSizeMaybe = Just . finiteBitSize
Example usage:
> import Data.Bits
> finiteBitSize (42 :: Int)
64
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With