Reputation: 3
I am an absolut noobie in coding. So I have a problem to solve. First I have a CSV file looking like this for example:
text.csv:
jan1,A
jan2,B
jan3,C
jan4,A
jan5,B
jan6,C
Now I want to import this "data" from the CSV in a Python programm, so that the variables are made directly from the CSV file:
jan1=A
jan2=B
...
Please remark that the A
should not be imported as a string, it`s a variable. When I import the CSV with CSV reader all the data is imported as a string?
Upvotes: 0
Views: 5512
Reputation: 8689
The problem is that the content of your CSV are not variables, but strings. Your CSV file contains literally the string "jan1,A". Now, it is possible in Python to manipulate variables directly via their name, because everything is (pretty much) dictionaries all the way down. However, be aware that you're venturing into a weird, unmaintainable and downright mad path. Messing with the 'internals' like that should only be used with the utmost precaution, and avoided if at all possible.
On to your problem: I mentionned that Python is dictionaries all the way down. Specifically, the vars()
, locals()
and globals()
might be what you're looking for:
>>> env = globals()
>>> a = 2
>>> env['a']
2
>>> env['b'] = 3
>>> b
3
What trickery is that ? Python maintains the state of its scope in dictionaries, and you can access these dictionaries directly, and manipulate them like any other dictionary. More specifically, locals()
and globals()
give you direct access to it. The module system makes it a bit more complex (as each module maintains its own globals
), but let us assume that you're operating in a single module.
So let's assume you have started your interpreter, and defined the following variables:
>>> A = 1
>>> B = 2
>>> C = 3
And you want to define the new variables jan1
, jan2
, jan3
, ... for these variables, according to the rules specified in your CSV. Let us ignore the CSV part for now (Danny Cullen's answer about the csv
module is pretty spot on for that), and let us assume that you've loaded your CSV into a list of tuples:
>>> csv
[('jan1', 'A'),
('jan2', 'B'),
('jan3', 'C'),
('jan4', 'A'),
('jan5', 'B'),
('jan6', 'C')]
Now you want to set variable jan1
with the value of variable A
. You can do that by modifying the globals()
dict of your module, and getting the locals()
value of your variable:
>>> glob = globals()
>>> loc = locals()
>>> glob['jan1'] = loc['A']
>>> jan1
1
Automating the whole reading is then trivial:
>>> for var_to_set, value_to_get in csv:
... glob[var_to_set] = loc[value_to_get]
>>>
>>> jan5
2
This will solve your problem, but let me emphasize what others have said: this is dangerous, completely unmaintainable and should generally be avoided ! One reason for that is that it's pretty straightforward to go from 'string' to 'variable' (we just did). On the other hand, it is impossible to go from variable back to string ! jan1
holds a value, and nothing else, it has no way of knowing that you refer to it as "jan1"
. So the process is lossy. On the other hand, carrying around various dictionaries with your mapping can always be 'converted back', without even going through these 'variable lookup' hoops (just keep the keys in sync).
In addition, I have mentionned above that modules have different globals. That rabbit hole goes deeper as functions, classes, modules, packages will all define their local scope, and variously refer to the globals and locals in different instances. This example works well on a tiny project, in a CLI, but it is impossible to scale this: keeping track of who adds what, where and how is rendered almost impossible when you start getting your hands dirty with the variable dictionaries.
If you really have to go the 'variable definition' way, I highly suggest you get familiar with the scoping rules in Python, and get prepared for quite a few headaches tracking down 'code that doesn't look like code'...
Upvotes: 2
Reputation: 2326
If you really want to achieve turning your CSV into variables, you can do:
row = "jan1,A"
exec("%s = %s" % (row.split(",")[0], row.split(",")[1]))
You have to define A
before though.
But please note that as other mentioned, it's really highly discouraged. The correct way to map data and code is using dictionaries.
Upvotes: 0
Reputation: 4010
It sounds like you want to "cross the boundary" between data and code by turning data into code. This is generally discouraged because it can be dangerous (what if someone added a command to your csv file that wiped your computer?).
Instead, just split the lines in the file by comma and save the first part, the variable name, as a dictionary key and make the second part the value:
csv_dict = {}
with open(csv_file, "r") as f:
for line in f:
key_val = line.strip().split(",")
csv_dict[key_val[0]] = key_val[1]
You can now access the keys/values via dictionary lookup:
>>> csv_dict["jan5"]
'B'
>>> csv_dict["jan4"]
'A'
>>> my_variable = data_dict["jan4"]
>>> my_variable
'A'
Upvotes: 1
Reputation: 100
What you're trying to do should be possible, but generally it isn't considered something good... Use a dictionary instead.
foovar = {'A': 1, 'B': 2, 'C': 3, ...} # Dictionary to store your 'variables'
jan1 = foovar['A']
jan2 = foovar['B']
...
if your first-column datas (jan1, jan2, ...) has to be used as variable names, use a dictionary for that too.
Upvotes: 0
Reputation: 1832
Use the python CSV module
https://docs.python.org/2/library/csv.html
import csv
with open('test.csv', 'rb') as csvfile:
reader = csv.reader(csvfile, delimiter=',', quotechar='"')
for row in reader:
print ', '.join(row)
Upvotes: 0