Python Forum
random.choice() takes two positional arguments, but three were given. - Printable Version

+- Python Forum (https://python-forum.io)
+-- Forum: Python Coding (https://python-forum.io/forum-7.html)
+--- Forum: General Coding Help (https://python-forum.io/forum-8.html)
+--- Thread: random.choice() takes two positional arguments, but three were given. (/thread-27251.html)



random.choice() takes two positional arguments, but three were given. - ShakeyPakey - May-31-2020

Hello.

In Python, I am using the random module. I have used the random.choice() method to randomly pick from two strings:

    import random

    variable = random.choice('string1','string2')
    print(variable)
However, when I run it, the following error occurs:

Error:
TypeError: choice() takes two positional arguments, but three were given.
I have also used

from numpy import random

instead of just

import random

but it still does not work.

How am I able to fix this error? Thank you.


RE: random.choice() takes two positional arguments, but three were given. - menator01 - May-31-2020

Should use a list
import random as rnd
mylist = []

for i in range(10):
   mylist.append(i)
print(rnd.choice(mylist))
print(rnd.choice(mylist))
print(rnd.choice(mylist))
Output:
9 2 8



RE: random.choice() takes two positional arguments, but three were given. - ShakeyPakey - May-31-2020

(May-31-2020, 12:36 PM)menator01 Wrote: Should use a list
import random as rnd
mylist = []

for i in range(10):
   mylist.append(i)
print(rnd.choice(mylist))
print(rnd.choice(mylist))
print(rnd.choice(mylist))
Output:
9 2 8

I think you have misunderstood my question or have replied to mine accidentally?


RE: random.choice() takes two positional arguments, but three were given. - menator01 - May-31-2020

Random may be a class therefore uses self as first argument.
Someone please correct me if I'm wrong.

That may be why your getting that error.


RE: random.choice() takes two positional arguments, but three were given. - GOTO10 - May-31-2020

(May-31-2020, 12:16 PM)ShakeyPakey Wrote: Hello.
In Python, I am using the random module. I have used the random.choice() method to randomly pick from two strings:
    import random
    variable = random.choice('string1','string2')
    print(variable)

The random.choice() method is expecting a sequence (list, tuple, or string) as its argument. The syntax you are using makes it seem like you are passing two separate strings as two separate arguments, when you mean for them to be seen as a single sequence. You can make this work properly by enclosing your two strings inside another set of parentheses so that it is recognized as a single tuple when random.choice() is called:
variable = random.choice(('string1','string2'))
The other, probably more common option would be to assign your strings to a tuple or list first, then call random.choice() with that variable:
tuple_choices = ('string1', 'string2')
variable = random.choice(tuple_choices)



RE: random.choice() takes two positional arguments, but three were given. - deanhystad - May-31-2020

If you type "help(random.choice) you get this:
Help on method choice in module random:

choice(seq) method of random.Random instance
    Choose a random element from a non-empty sequence.
The two interesting pieces of information are that the function is expecting a "sequence" argument, and that the function is not a function.

In Python, a "sequence" is a container data type. Strings are sequences because they are made up of individual letters that you can access. Lists and tuples because they too are made up of things that can be independently accessed.

Your call "random.choice('string1','string2')" would have worked if you left out the second string. It would return a randomly chosen letter from 'string1'. Probably not what you want. To randomly choose between 'string1' and 'string2' you need to put them in a sequence. Because they are smaller and faster I would use a tuple.
random.choice(('string1','string2'))
But why did your error message say "choice() takes two positional arguments, but three were given." Where does it see three positional arguments? This was the other interesting thing learned from help. random.choice is not a function.

If you type "type(random.choice)" it returns <class 'method'>. choice is a method of class Random. It doesn't look like a method. Normally a method is called using an instance; instance.method(), but when you do this:
import random
x = random.choice(('string1', 'string2'))
the "random" is a module, not an instance of class Random. random tells Python to look in the "random" namespace to find "choice" So how can random.choice() call a method and where is the instance?

This confusing syntactic magic is performed using a singleton. When you import random it creates a single instance of class Random. "_inst = Random()". Then it creates some global variables to access the Random methods "choices = _inst.choices". This makes "Random" look like a collection of functions instead of a class, but you are really creating an instance and calling instance methods. When you call "random.choice('string1', 'string2')" your are actually calling "random._inst.choice(string1', 'string2')" which is really "random.Random.choice(_inst, string1', 'string2')". Look at that! Three positional arguments.