Using User Input to Index List in Python - python

I can't understand what I am doing wrong with this method. It is called from another in class method as such:
def equip_menu(self): # this is not the actual method, but equip_choice is used only in the following lines
#snipped code
equip_choice = Input("Input the number of the item you want to equip:\n")
self.select_from_list_equip(equip_choice)
and this is the method throwing error:
def select_from_list_equip(self, equip_choice): # Trying to select item in list self.backpack
item_to_equip = self.backpack[equip_choice]
print("*DEBUG* Equip chosen:", item_to_equip.name)
playeritems.equip(item_to_equip)
I get the error:
"classes.py", line 109, in select_from_list_equip
item_to_equip = self.backpack[count]
TypeError: list indices must be integers or slices, not str"
So I tried making equip_choice an integer, even though I just try inputting digits without decimals and still get the error. I am in the opinion that I am not trying to use a string as list index, but obviously I am wrong. So I tried to force equip_choice to become an integer like this:
def select_from_list_equip(self, equip_choice):
int(equip_choice)
item_to_equip = self.backpack[equip_choice]
print("*DEBUG* Equip chosen:", item_to_equip.name)
playeritems.equip(item_to_equip)
But I still get the same identical error. Why can't I use the value of equip_choice as list index? I must be missing something very obvious and basic I am blind to?

Input() returns a string. You will need to use int() to convert to an integer.
input() resource

Related

How do you simplify .str.contains code with multiple contains variables?

I am using the Series.str.contains() function to find if a value in a dictionary is contained in a string from a specific column. My code works, but I am trying to simplify it.
I tried using a for loop to go through the values in a list. My attempt is down below.
total_joined_list=[joined_groc_lst,joined_util_lst]
for i in range(len(total_joined_list)):
groc_amount,util_amount=abs(round(df.loc[df['Description'].str.contains('\b'+i+'\b',na=False),'Amount'].sum(),2))
Here is the current working code.
joined_groc_lst = '|'.join(expenses_dict['Groceries'])
joined_util_lst = '|'.join(expenses_dict['Utilities'])
groc_amount=abs(round(df.loc[df['Description'].str.contains('\b'+joint_groc_lst+'\b',na=False),
'Amount'].sum(),2))
util_amount=abs(round(df.loc[df['Description'].str.contains('\b'+joint_util_lst+'\b',na=False),
'Amount'].sum(),2))
I expect my function to create two variables; groc_amount and util_amount, and I would be able to print my results. I got this error "TypeError: can only concatenate str (not "int") to str" and then added str() to the i in my for loop and get the following error "TypeError: cannot unpack non-iterable int object"
total_joined_list=[joined_groc_lst,joined_util_lst]
groc_amount, util_amount = (abs(round(df.loc[df['Description'].str.contains(f'\b{e}\b',na=False),'Amount'].sum(),2)) for e in total_joined_list)
I have change your forloop into a generator that allow unpacking data in order to get each items in the list.

Instancing maya objects with a sequential suffix, object name string not seen by cmds.instance

I have a question about string usage in lists in python for Maya. I am writing a script meant to take a selected object, then instance it 100 times with random translate, scale, and orient attributes. The script itself works and does what it's meant to, however I'm not being able to decipher how to instance the objects with the original object name, and then add a suffix that ends with "_instance#", where # assigns 1, 2, 3, etc. in order to the copies of the original mesh. This is where I'm at so far:
#Capture selected objects, sort into list
thing = MC.ls(sl=True)
print thing
#Create instances of objects
instanceObj = MC.instance(thing, name='thing' + '_instance#')
This returns a result that looks like "thing_instance1, thing_instance2".
Following this, I figured the single quote around the string for the object was causing it to just name it "thing", so I attempted to write it as follows
MC.instance(thing, name=thing + '_instance1'
I guess because instance uses a list, it's not accepting the second usage of the string as valid and returns a concatenate error. I've tried rewriting this a few times and the closest I get is with
instanceObj = MC.instance(thing)
which results in a list of (pCube1,2,3,4), but is lacking the suffix.
I'm not sure where to go from here to end up with a result where the instanced objects are named with the convention "pCube1_instance1, pCube1_instance2" etc.
Any assistance would be appreciated.
It is not clear if you want to use only one source object or more. In any case the
MC.ls(sl=True)
returns a list of strings. And concatenating a list and a string does not work. So use thing[0] or simply
MC.ls(sl=True)[0]
If you get errormessages, please always include the message in your question, it helps a lot to see what error appears.

Why is this an index error?

This is my first post, so I apologize if this has been answered previously. I have tried to look through the Python 3 documentation on string formatting and lists, and reviewed similar formatting questions here on SO.
I want to take the string (data1), break it into a list (bigData), and print out a statement using the list items. Eventually, the idea would be to read in a csv file, break it up, and print out a response, but I've tried to simplify the process since there's an error.
"Hello, John Doe. Your current balance is $53.44."
However, I'm not sure why the following code is throwing an IndexError, much less a tuple index.
data1 = "John,Doe,53.44"
bigData = data1.split(",")
bigData[-1] = float(bigData[-1])
print(bigData) # test - []'s indicate a list, not tuple?
greeting = "Hello, {} {}. Your current balance is ${}."
print(greeting.format(bigData))
My guess is that bigData is heterogeneous, which implies a tuple. If I substitute a string value instead of 53.44 (so data1 and bigData are homogeneous), it throws the same error.
data1 = "John,Doe,random"
bigData = data1.split(",")
print(bigData) # test - []'s indicate a list, not tuple?
greeting = "Hello, {} {}. Your current balance is {}."
print(greeting.format(bigData))
However, if I convert the original to Python 2.x string formatting, it formats correctly without an error.
data1 = "John,Doe,53.44"
bigData = data1.split(",")
bigData[-1] = float(bigData[-1])
print(bigData) # test - []'s indicate a list, not tuple?
greeting = "Hello, %s %s. Your current balance is $%.2f."
print(greeting % tuple(bigData))
Why is it converting my string to a tuple?
How do I write this work in Python 3?
Thank you.
Use the splat (*) to unpack your arguments (your format string wants three arguments but you only give it one, a list containter).
print(greeting.format(*bigData))
Also, you may want:
bigData[-1] = str(round(float(bigData[-1]), 2))
The str.format method takes positional arguments, not a single list. You need to unpack your list bigData using the * operator:
data1 = "John,Doe,random"
bigData = data1.split(",")
print(bigData) # test - []'s indicate a list, not tuple?
greeting = "Hello, {} {}. Your current balance is {}."
print(greeting.format(*bigData)) # here's the change
You're correct that bigData is a list, not a tuple, str.split returns a list.
The str.split() method returns a list, by definition.
I think you've misunderstood something you've read - heterogeneous vs. homogeneous refer to typical use cases of tuples vs. lists. Having the types of all the elements match or not does not magically cause the container to change to the other type!
I can see how this is surprising, though what surprises me is that the traceback doesn't show that the exception occurs in the format call.
Python's lists can be heterogenous just like tuples; this is because the common type they store is object references, which all things in Python are. The tuple is actually the argument list to the format method, in this case (bigData,). It ran out of arguments when looking for things to format, since you had three {} placeholders but only one argument (the list bigData). You can use greeting.format(*bigData) to unpack the list and use its contents as arguments.
The % formatting doesn't encounter this error because it actually expects a tuple (or one item) in the right operand.
A more idiomatic and legible approach might actually be to go to the csv module already:
import csv, io
data1 = "John,Doe,random"
for row in csv.DictReader(io.StringIO(data1),
"givenname surname balance".split()):
greeting = "Hello, {givenname} {surname}. Your current balance is {balance}."
print(greeting.format(**row))
This lets us assign meaningful names to the columns, including reordering them in the format string if needed. I've left out the float conversion, and by the way, decimal.Decimal may be better for that use.

python how to index a list and then select randomly from it

I have an "initial_list" that contains 100 strings. I'd like initial_list to index using "member". And from "member" I need to select 100 random members of the initial_list then I need to transfer them to a "second_list". My strategy is as follows:
initial_list=[content]
second_list=[]
for member in range(0,len(initial_list)):
randommember=random.randint(0,99)
second_list.append(pop_array[randommember])
However the command keeps returning "'module' object has no attribute 'int'", because I can't seem to utilise member such that the random.int function can iterate through it.
I am aware that I could do this using strings and random.choice() but I have ulterior reasons for using lists and random.int().
Any tips?
First, it's random.randint, not random.int. Second, you can't index an integer with another integer like you're doing with [member]. Third, you can simply use second_list.append(random.choice(pop_array)).

"TypeError: float argument must be a string or a number, not a list." converting a list of strings to a list of floats

I am trying to convert a list of strings into a list of floats. I have tried list comprehension, mapping, and simply writing it out in a for loop. I don't really want to use mapping since I can't seem to get it back into a proper list even with list(map).
So far none of my attempts have worked because I am having trouble finding the correct syntax for Python 3x. My latest attempt seems to show promise, but I keep getting the following error.
Traceback (most recent call last):
File "G:/test.py", line 56, in <module>
heartdis_flt.append(float(item))
TypeError: float() argument must be a string or a number, not 'list'
This is the code I am using:
heartdis = heartdis[5:]
heartdis_flt = []
for item in heartdis:
heartdis_flt.append(float(item))
print(heartdis_flt)
heartdis is a list of strings created from a CSV file.
Can someone explain the correct syntax or maybe some flaw in my logic?
I found something that will work. I used itertools to change the list of list into one list then converted it all to floats.
heartdis = heartdis[5:]
heartdis_flt = []
heartdis2 = list(itertools.chain.from_iterable(heartdis))
for item in heartdis2:
heartdis_flt.append(float(item))
print(heartdis_flt)
Like #utdemir commented, the problem with your code is that you are treating a list as a string. You indeed could use itertools.chain, but maybe you want to change the way you are reading from heartdis in the first place. I don't know how you are reading your CSV file, but if you are using the csv module, I reckon you should not be getting list of lists as outputs. Anyway, something you should check in my opinion.

Categories

Resources