Reputation: 77
I have a 2 dimensional numpy matrix whose type is numpy.ndarray
of uint8
.
Now when I perform np.square
on the array, it does not return the expected result.
Here's an example of the code on the console and its output after I create the numpy array:
arr[0, 0]
outputs 203
Now,
np.square(203)
outputs 41209
But,
np.square(arr[0, 0])
outputs 249
This odd behavior was also observed for the np.sqrt method.
Upvotes: 0
Views: 304
Reputation: 231355
np.square
like other ufunc
can return results with various dtypes. Looks like it 'prefers' to return a matching dtype:
In [109]: np.square(np.array([203], 'uint8'),dtype=int)
Out[109]: array([41209])
In [110]: np.square(np.array([203], 'uint8'),dtype='uint8')
Out[110]: array([249], dtype=uint8)
In [111]: np.square(np.array([203], 'uint8'))
Out[111]: array([249], dtype=uint8)
In [112]: np.square(np.array([203], 'uint8'),dtype='uint8')
Out[112]: array([249], dtype=uint8)
In [113]: np.square(np.array([203], 'uint8'),dtype='uint16')
Out[113]: array([41209], dtype=uint16)
In [114]: np.square(np.array([203], 'uint8'),dtype='int')
Out[114]: array([41209])
In [115]: np.square(np.array([203], 'uint8'),dtype='float')
Out[115]: array([41209.])
https://numpy.org/doc/stable/reference/ufuncs.html#casting-rules
and under signature
parameter.
In [118]: np.square.types
Out[118]:
['b->b',
'B->B', # uint8
'h->h',
'H->H',
'i->i',
...]
There are more details in handling of casting and dtypes, but the basic point is that if using 'exotic' dtypes like unit8
beware of overflow etc. Even with 'int32' overflow can be problem, but at much larger numbers. A more common problem arise when doing some calculation on integers that results in floats.
A recent SO about dtypes with /=
operator.
numpy.array's have bizarre behavior with /= operator?
Many times I've had to ask SO questions - what's the shape
, what's the dtype
. Those are fundamental properties of a numpy
array. Getting those right is 80% of the debugging battle.
Upvotes: 1
Reputation:
According to numpy.org np.uint8
is Unsigned integer (0 to 255)
import numpy as np
arr = np.array([[203, 32, 45, 34], [34,322,780,54]])
arr1 = arr.astype('uint8')
arr2 = arr.astype('uint16')
sq = np.square(203)
sq8 = np.square(arr1[0,0])
sq16 = np.square(arr2[0,0])
sq, sq8, sq16, type(sq), type(sq8), type(sq16)
output:
(41209, 249, 41209, numpy.intc, numpy.uint8, numpy.uint16)
41209
is 249
in uint8
:
num = np.array([41209])
num1 = arr.astype('uint8')
num1
>>> array([249], dtype=uint8)
Upvotes: 3