41 if (old_dims.
length () == 2 && old_dims(0) == 1)
43 else if (old_dims.
length () == 2 && old_dims (0) == 0 && old_dims (1) == 0)
49 template <
class ArrayType>
61 data =
reinterpret_cast<const void *
> (array.data ());
62 byte_size = array.byte_size ();
64 old_dims = array.dims ();
67 template <
class ArrayType>
72 typedef typename ArrayType::element_type T;
75 if (n * static_cast<int> (
sizeof (T)) == byte_size)
78 T *dest = retval.fortran_vec ();
79 std::memcpy (dest, data, n *
sizeof (T));
85 error (
"typecast: incorrect number of input values to make output value");
91 DEFUN (typecast, args, ,
93 @deftypefn {Built-in Function} {} typecast (@var{x}, @var{class})\n\
94 Return a new array @var{y} resulting from interpreting the data of\n\
95 @var{x} in memory as data of the numeric class @var{class}. Both the class\n\
96 of @var{x} and @var{class} must be one of the built-in numeric classes:\n\
112 \"double complex\"\n\
113 \"single complex\"\n\
118 the last two are reserved for @var{class}; they indicate that a\n\
119 complex-valued result is requested. Complex arrays are stored in memory as\n\
120 consecutive pairs of real numbers. The sizes of integer types are given by\n\
121 their bit counts. Both logical and char are typically one byte wide;\n\
122 however, this is not guaranteed by C++. If your system is IEEE conformant,\n\
123 single and double should be 4 bytes and 8 bytes wide, respectively.\n\
124 @qcode{\"logical\"} is not allowed for @var{class}. If the input is a row\n\
125 vector, the return value is a row vector, otherwise it is a column vector. \n\
126 If the bit length of @var{x} is not divisible by that of @var{class}, an\n\
129 An example of the use of typecast on a little-endian machine is\n\
133 @var{x} = uint16 ([1, 65535]);\n\
134 typecast (@var{x}, \"uint8\")\n\
135 @result{} [ 1, 0, 255, 255]\n\
138 @seealso{cast, bitunpack, bitpack, swapbytes}\n\
143 if (args.length () == 2)
146 const void *data = 0;
191 byte_size, old_dims, frame);
194 byte_size, old_dims, frame);
205 error (
"typecast: invalid input class: %s",
208 std::string numclass = args(1).string_value ();
212 else if (numclass ==
"char")
214 (data, byte_size, old_dims), array.
is_dq_string () ?
'"'
216 else if (numclass[0] ==
'i')
218 if (numclass ==
"int8")
219 retval = reinterpret_copy<int8NDArray> (data, byte_size, old_dims);
220 else if (numclass ==
"int16")
221 retval = reinterpret_copy<int16NDArray> (data, byte_size, old_dims);
222 else if (numclass ==
"int32")
223 retval = reinterpret_copy<int32NDArray> (data, byte_size, old_dims);
224 else if (numclass ==
"int64")
225 retval = reinterpret_copy<int64NDArray> (data, byte_size, old_dims);
227 else if (numclass[0] ==
'u')
229 if (numclass ==
"uint8")
230 retval = reinterpret_copy<uint8NDArray> (data, byte_size, old_dims);
231 else if (numclass ==
"uint16")
232 retval = reinterpret_copy<uint16NDArray> (data, byte_size,
234 else if (numclass ==
"uint32")
235 retval = reinterpret_copy<uint32NDArray> (data, byte_size,
237 else if (numclass ==
"uint64")
238 retval = reinterpret_copy<uint64NDArray> (data, byte_size,
241 else if (numclass ==
"single")
242 retval = reinterpret_copy<FloatNDArray> (data, byte_size, old_dims);
243 else if (numclass ==
"double")
244 retval = reinterpret_copy<NDArray> (data, byte_size, old_dims);
245 else if (numclass ==
"single complex")
246 retval = reinterpret_copy<FloatComplexNDArray> (data, byte_size,
248 else if (numclass ==
"double complex")
249 retval = reinterpret_copy<ComplexNDArray> (data, byte_size, old_dims);
252 error (
"typecast: cannot convert to %s class", numclass.c_str ());
260 template <
class ArrayType>
264 typedef typename ArrayType::element_type T;
266 = bitp.
numel () / (
sizeof (T) * std::numeric_limits<unsigned char>::digits);
268 if (n * static_cast<int> (
sizeof (T)) * std::numeric_limits<unsigned char>::digits == bitp.
numel ())
274 char *packed =
reinterpret_cast<char *
> (retval.fortran_vec ());
281 for (
int j = 1; j < std::numeric_limits<unsigned char>::digits; j++)
285 bits += std::numeric_limits<unsigned char>::digits;
292 error (
"bitpack: incorrect number of bits to make up output value");
297 DEFUN (bitpack, args, ,
299 @deftypefn {Built-in Function} {@var{y} =} bitpack (@var{x}, @var{class})\n\
300 Return a new array @var{y} resulting from interpreting an array\n\
301 @var{x} as raw bit patterns for data of the numeric class @var{class}.\n\
302 @var{class} must be one of the built-in numeric classes:\n\
320 The number of elements of @var{x} should be divisible by the bit length of\n\
321 @var{class}. If it is not, excess bits are discarded. Bits come in\n\
322 increasing order of significance, i.e., @code{x(1)} is bit 0, @code{x(2)} is\n\
323 bit 1, etc. The result is a row vector if @var{x} is a row vector, otherwise\n\
324 it is a column vector.\n\
325 @seealso{bitunpack, typecast}\n\
330 if (args.length () == 2 && args(0).is_bool_type ())
334 std::string numclass = args(1).string_value ();
338 else if (numclass ==
"char")
339 retval =
octave_value (do_bitpack<charNDArray> (bitp),
'\'');
340 else if (numclass[0] ==
'i')
342 if (numclass ==
"int8")
343 retval = do_bitpack<int8NDArray> (bitp);
344 else if (numclass ==
"int16")
345 retval = do_bitpack<int16NDArray> (bitp);
346 else if (numclass ==
"int32")
347 retval = do_bitpack<int32NDArray> (bitp);
348 else if (numclass ==
"int64")
349 retval = do_bitpack<int64NDArray> (bitp);
351 else if (numclass[0] ==
'u')
353 if (numclass ==
"uint8")
354 retval = do_bitpack<uint8NDArray> (bitp);
355 else if (numclass ==
"uint16")
356 retval = do_bitpack<uint16NDArray> (bitp);
357 else if (numclass ==
"uint32")
358 retval = do_bitpack<uint32NDArray> (bitp);
359 else if (numclass ==
"uint64")
360 retval = do_bitpack<uint64NDArray> (bitp);
362 else if (numclass ==
"single")
363 retval = do_bitpack<FloatNDArray> (bitp);
364 else if (numclass ==
"double")
365 retval = do_bitpack<NDArray> (bitp);
366 else if (numclass ==
"single complex")
367 retval = do_bitpack<FloatComplexNDArray> (bitp);
368 else if (numclass ==
"double complex")
369 retval = do_bitpack<ComplexNDArray> (bitp);
372 error (
"bitpack: cannot pack to %s class", numclass.c_str ());
380 template <
class ArrayType>
384 typedef typename ArrayType::element_type T;
386 * std::numeric_limits<unsigned char>::digits;
390 const char *packed =
reinterpret_cast<const char *
> (array.fortran_vec ());
399 for (
int j = 1; j < std::numeric_limits<unsigned char>::digits; j++)
400 bits[j] = (c >>= 1) & 1;
401 bits += std::numeric_limits<unsigned char>::digits;
407 DEFUN (bitunpack, args, ,
409 @deftypefn {Built-in Function} {@var{y} =} bitunpack (@var{x})\n\
410 Return an array @var{y} corresponding to the raw bit patterns of\n\
411 @var{x}. @var{x} must belong to one of the built-in numeric classes:\n\
429 The result is a row vector if @var{x} is a row vector; otherwise, it is a\n\
431 @seealso{bitpack, typecast}\n\
436 if (args.length () == 1
437 && (args(0).is_numeric_type () || args(0).is_string ()))
479 error (
"bitunpack: invalid input class: %s",