# problem with decimate in scipy 0.18

I use scipy.signal.decimate to downsample a large spectroscopic data-set. This has worked superbly so far.

yy = decimate(data.row(i).buffer, n2, ftype = "fir")


I used successively to downsample the spectrum to several lower resolutions.

When I moved from scipy 0.17 to 0.18 (actually 0.18.1) during of a python3 port, a problem appeared. The first downsampling works, on all the rows; but the next one crashes with the following message:

File "..../lib/python3.5/site-packages/scipy/signal/signaltools.py", line 3049, in decimate
raise TypeError("q must be an integer")
TypeError: q must be an integer


I looked to the code, but with no avail. I also tried the new zero_phase=True argument, but did not help. Needless to say that my n2 argument above IS an integer, the second time as well as the first time!

Any pointers ?

• Have you tried int(n2) in function call? Remember that Python3 might yield floats in places where they were integers before (the division operation has changed). Just in case, what is the output of print(type(n2))? – jojek Apr 26 '17 at 11:57

I have found the bug ! n2 is indeed a integer in my case, but its not an int()

print(type(n2)) gives: <class 'numpy.int64'> !!!

In the previous version of scipy, it was already a numpy.int64 but it was working correctly.

Maybe a test slightly too stringent...

Thanks for helping everyone.

• Actually it's been this way since the function was created 8 years ago :) So it must be something in your code. Anyway, I made a change to make it less strict, so it will accept int(2), 2.0, numpy.array(2), Fraction(2), etc. I'm fixing the same issue in other functions and then will submit the pull request. :D – endolith Apr 28 '17 at 16:11
• This is inside a big loop in a big application. The n2 parameters comes from another scipy/numpy computation, which might have changed. If there is any interest, I might investigate. – Marc-André Delsuc Apr 29 '17 at 8:13
• github.com/scipy/scipy/pull/7351 – endolith Apr 29 '17 at 11:22

The input n2 must be an actual integer (like 3), not a float with integer value (like 3.0). Replace n2 with int(n2) in the function call:

yy = decimate(data.row(i).buffer, int(n2), ftype = "fir")


signaltools.py contains:

def decimate(x, q, n=None, ftype='iir', axis=-1, zero_phase=None):
...
if not isinstance(q, int):
raise TypeError("q must be an integer")

if n is not None and not isinstance(n, int):
raise TypeError("n must be an integer")


Probably because it's used in a slice and NumPy slices won't accept non-integers anymore.

(I would think the function should be more forgiving and check for int(q) == q instead, and then convert to int internally if needed for slicing. I'll try to change it if I have time.)