563

How do I create an ascending list between two values? For example, a list between 11 and 16:

[11, 12, 13, 14, 15, 16]
Mateen Ulhaq
  • 24,552
  • 19
  • 101
  • 135
lorde
  • 5,813
  • 2
  • 14
  • 9

12 Answers12

998

Use range. In Python 2, it returns a list directly:

>>> range(11, 17)
[11, 12, 13, 14, 15, 16]

In Python 3, range is an iterator. To convert it to a list:

>>> list(range(11, 17))
[11, 12, 13, 14, 15, 16]

Note: The second number in range(start, stop) is exclusive. So, stop = 16+1 = 17.


To increment by steps of 0.5, consider using numpy's arange() and .tolist():

>>> import numpy as np
>>> np.arange(11, 17, 0.5).tolist()

[11.0, 11.5, 12.0, 12.5, 13.0, 13.5,
 14.0, 14.5, 15.0, 15.5, 16.0, 16.5]

See: How do I use a decimal step value for range()?

Mateen Ulhaq
  • 24,552
  • 19
  • 101
  • 135
Jared
  • 25,627
  • 7
  • 56
  • 61
  • 2
    Awesome! Exactly what I was looking for! Is there also a way to increment by smaller values like 0.5 than just 1? so [11.0, 11.5, 12.0 ...... 16.0] – lorde Aug 16 '13 at 04:50
  • 4
    @lorde You can increment by more than 1 with a third `step` parameter but that's still an int -- not float. You can't do that exactly in the standard lib. – Jared Aug 16 '13 at 04:53
  • @Jared can I make a list by dropping some value after some interval. like [1,2,3,5,6,7,9,10,11,13,14,15,17,18,19] –  Jun 07 '16 at 09:12
  • 2
    Good for telling about Python 2.x and 3.x. – Sigur Apr 15 '17 at 16:24
  • 1
    If you're working in circumstances where numpy is unwanted, consider (where x=11, y=17, and step=0.5 as above): a_range = [x]+[x+(step*i) for i in range(int((y-x)/step))] – TheLoneDeranger Oct 03 '18 at 17:53
  • this is the best answer I ever searched haha, I was thinking of using forloop for it.. such a bad idea in my mind – Karam Qusai Dec 30 '19 at 13:37
  • Concerning the edit: using Python 3.7.6 with Numpy 1.18.1, using other floats as step size, e.g. `np.arange(11, 17, 0.1).tolist()`), results in entries with `11.299999999999999`. – YTZ Jun 18 '20 at 13:37
  • I believe the range function now has a built-in step parameter (default=1) now! – Lathryx Jul 02 '20 at 03:43
  • If you wanted to increment by 0.5 without having to install `numpy`, you could use `list(i / 10 for i in range(110, 170, 5))` – Pyzard Jun 06 '22 at 17:24
42

You seem to be looking for range():

>>> x1=11
>>> x2=16
>>> range(x1, x2+1)
[11, 12, 13, 14, 15, 16]
>>> list1 = range(x1, x2+1)
>>> list1
[11, 12, 13, 14, 15, 16]

For incrementing by 0.5 instead of 1, say:

>>> list2 = [x*0.5 for x in range(2*x1, 2*x2+1)]
>>> list2
[11.0, 11.5, 12.0, 12.5, 13.0, 13.5, 14.0, 14.5, 15.0, 15.5, 16.0]
devnull
  • 118,548
  • 33
  • 236
  • 227
16

Try:

range(x1, x2+1)  

That is a list in Python 2.x and behaves mostly like a list in Python 3.x. If you are running Python 3 and need a list that you can modify, then use:

list(range(x1, x2+1))
ah bon
  • 9,293
  • 12
  • 65
  • 148
Mike Housky
  • 3,959
  • 1
  • 17
  • 31
8

Use list comprehension in python. Since you want 16 in the list too.. Use x2+1. Range function excludes the higher limit in the function.

list=[x for x in range(x1, x2+1)]
ah bon
  • 9,293
  • 12
  • 65
  • 148
Bhargav Ponnapalli
  • 9,224
  • 7
  • 36
  • 45
  • 4
    If you use `range()` no need to use a list comprehension – Billal Begueradj Apr 17 '18 at 10:59
  • @BillalBegueradj In Python3, range() returns a generator-like object instead of a list. It's basically the same as xrange() in Python 2. You're right that list comprehension isn't needed. The list() builtin function is easier: `list(range(x1, x2+1))`. – Mike Housky Jan 19 '20 at 05:14
  • @MikeHousky no, `range` is **absolutely not** a generator-like object. It is a sequence type object. Unless you want to do things like append to the sequence, you can probably just use the range object directly. – juanpa.arrivillaga Oct 19 '21 at 15:37
  • 1
    Using a list-comprehension here is pointless. `[x for x in whatever]` should always just be `list(whatever)` – juanpa.arrivillaga Oct 19 '21 at 15:37
8

If you are looking for range like function which works for float type, then here is a very good article.

def frange(start, stop, step=1.0):
    ''' "range()" like function which accept float type''' 
    i = start
    while i < stop:
        yield i
        i += step
# Generate one element at a time.
# Preferred when you don't need all generated elements at the same time. 
# This will save memory.
for i in frange(1.0, 2.0, 0.5):
    print i   # Use generated element.
# Generate all elements at once.
# Preferred when generated list ought to be small.
print list(frange(1.0, 10.0, 0.5))    

Output:

1.0
1.5
[1.0, 1.5, 2.0, 2.5, 3.0, 3.5, 4.0, 4.5, 5.0, 5.5, 6.0, 6.5, 7.0, 7.5, 8.0, 8.5, 9.0, 9.5]
Rajesh Surana
  • 883
  • 1
  • 10
  • 15
  • Why not the one-liner instead? `start = 2; step =1; end = 10; z= np.array(range(start*step,step*end))/step; print(z)` – Mohd Nov 11 '20 at 10:02
7

assuming you want to have a range between x to y

range(x,y+1)

>>> range(11,17)
[11, 12, 13, 14, 15, 16]
>>>

use list for 3.x support

v2b
  • 1,436
  • 9
  • 15
5

In python you can do this very eaisly

start=0
end=10
arr=list(range(start,end+1))
output: arr=[0,1,2,3,4,5,6,7,8,9,10]

or you can create a recursive function that returns an array upto a given number:

ar=[]
def diff(start,end):
    if start==end:
        d.append(end)
        return ar
    else:
        ar.append(end)
        return diff(start-1,end) 

output: ar=[10,9,8,7,6,5,4,3,2,1,0]

5

I got here because I wanted to create a range between -10 and 10 in increments of 0.1 using list comprehension. Instead of doing an overly complicated function like most of the answers above I just did this

simple_range = [ x*0.1 for x in range(-100, 100) ]

By changing the range count to 100 I now get my range of -10 through 10 by using the standard range function. So if you need it by 0.2 then just do range(-200, 200) and so on etc

Jose
  • 1,959
  • 20
  • 21
4

While @Jared's answer for incrementing works for 0.5 step size, it fails for other step sizes due to rounding issues:

np.arange(11, 17, 0.1).tolist()
# [11.0,11.1,11.2,11.299999999999999, ...   16.79999999999998, 16.899999999999977]

Instead I needed something like this myself, working not just for 0.5:

# Example 11->16 step 0.5
s = 11
e = 16
step = 0.5
my_list = [round(num, 2) for num in np.linspace(s,e,(e-s)*int(1/step)+1).tolist()]
# [11.0, 11.5, 12.0, 12.5, 13.0, 13.5, 14.0, 14.5, 15.0, 15.5, 16.0]

# Example 0->1 step 0.1
s = 0
e = 1
step = 0.1
my_list = [round(num, 2) for num in np.linspace(s,e,(e-s)*int(1/step)+1).tolist()]
# [0.0, 0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.0]
YTZ
  • 876
  • 11
  • 26
3

Every answer above assumes range is of positive numbers only. Here is the solution to return list of consecutive numbers where arguments can be any (positive or negative), with the possibility to set optional step value (default = 1).

def any_number_range(a,b,s=1):
""" Generate consecutive values list between two numbers with optional step (default=1)."""
if (a == b):
    return a
else:
    mx = max(a,b)
    mn = min(a,b)
    result = []
    # inclusive upper limit. If not needed, delete '+1' in the line below
    while(mn < mx + 1):
        # if step is positive we go from min to max
        if s > 0:
            result.append(mn)
            mn += s
        # if step is negative we go from max to min
        if s < 0:
            result.append(mx)
            mx += s
    return result

For instance, standard command list(range(1,-3)) returns empty list [], while this function will return [-3,-2,-1,0,1]

Updated: now step may be negative. Thanks @Michael for his comment.

Denis Rasulev
  • 3,744
  • 4
  • 33
  • 47
  • 1
    This assumes your step is positive. – Michael Jan 10 '18 at 13:55
  • @Michael, good point. I've updated the code, so now you can have negative steps :) – Denis Rasulev Jan 11 '18 at 11:11
  • @tgikal, that's right. But what if you don't know what values will be assigned to the arguments of your function and you need sorted return? – Denis Rasulev Sep 06 '18 at 06:15
  • I don't see any additional features your custom function does that cannot be accomplished using the builtin range function, I guess an example of the improvement would be great, since your current example is basically `i_min = -3, i_max = 1` `any_number_range(i_max, i_min))` returns `[-3,-2,-1,0,1]` But, builtin `list(range(i_min, i_max + 1))` will return the same values. – tgikal Sep 06 '18 at 20:43
  • Try using a negative step when the sequence is decreasing `list(range(1,-3, -1))` – Juan Antonio Roldán Díaz Jul 17 '19 at 08:04
3

The most elegant way to do this is by using the range function however if you want to re-create this logic you can do something like this :

def custom_range(*args):
    s = slice(*args)
    start, stop, step = s.start, s.stop, s.step
    if 0 == step:
        raise ValueError("range() arg 3 must not be zero")
    i = start
    while i < stop if step > 0 else i > stop:
        yield i
        i += step

>>> [x for x in custom_range(10, 3, -1)]

This produces the output:

[10, 9, 8, 7, 6, 5, 4]

As expressed before by @Jared, the best way is to use the range or numpy.arrange however I find the code interesting to be shared.

Michael
  • 2,436
  • 1
  • 36
  • 57
0

@YTZ's answer worked great in my case. I had to generate a list from 0 to 10000 with a step of 0.01 and simply adding 0.01 at each iteration did not work due to rounding issues.

Therefore, I used @YTZ's advice and wrote the following function:

import numpy as np


def generate_floating_numbers_in_range(start: int, end: int, step: float):
    """
    Generate a list of floating numbers within a specified range.

    :param start: range start
    :param end: range end
    :param step: range step
    :return:
    """
    numbers = np.linspace(start, end,(end-start)*int(1/step)+1).tolist()
    return [round(num, 2) for num in numbers]