3
p1 = (0, 10, 1)
p2 = (0, -20, -2)
p3 = (0,10,2)

Hi,

I have the above code and I'd simply like a quick way to count how many items are in each range without iterating through it? (its part of a few nested loops). So p1 would return 9.

Also is there a better way to pass those variables in to the range function?

right now i'm suing:

range(p1[0], p1[1], p1[2])
Leon
  • 2,926
  • 1
  • 25
  • 34
novawaly
  • 1,051
  • 3
  • 12
  • 27
  • 2
    Shouldn't `p1` return 10, not 9? As this range contains the numbers from 0 to 9 inclusive, in other words, all the digits, which are 10? – Leon Aug 23 '18 at 20:38
  • Not a dupe, but see: https://stackoverflow.com/q/30081275/4799172 – roganjosh Aug 23 '18 at 20:45

4 Answers4

9
>>> p1 = (0, 10, 1)
>>> len(range(*p1))
10

range objects are clever and don't require iteration to calculate the length.

wim
  • 338,267
  • 99
  • 616
  • 750
2

The virtue of this is that you don't have to create a new object to calculate.

def c(p):
  return max((p[1] - p[0]) // p[2], 0)

c(p1)

10
piRSquared
  • 285,575
  • 57
  • 475
  • 624
  • 3
    it works only for valid parameters. For instance, with (0,10,-1) it would return `-10` while `len(range(0,10,-1))` would return `0`. I would change it to `return max(0, p[1] - p[0]) // p[2])` – abc Aug 23 '18 at 20:49
  • This has the advantage that it works for `p = sys.maxsize, sys.maxsize**2, 1` – Chris_Rands Aug 23 '18 at 21:04
1

Maybe simple math? Just calculate difference between start and stop and devoid it on step size. And, finely subtract one from the result

((p[1]-p[0])/p[2]) - 1
0

This is a good example to use the unpacking operator *. If you have p1 = (0,10,1) then you have to unpack the tuple p1 in order to pass its elements as arguments of range function. Then you can just use the len function to get the length of the range, as follows:

print(len(range(*p1)))  # 10
Laurent H.
  • 6,316
  • 1
  • 18
  • 40