1

I have many python files all with the same variable names but different values. Something like this would be in one:

var_one = 'happy'
var_two = '2345'
var_three = '-24.24'
var_four = 'Chocolate'

I need to write a Python script that can read these files and when I ask for var_one it returns happy. If I ask for var_two it returns 2345 and so on and so forth.

Right now I have a python two compliant toolbox that does this using something along the lines of:

for fname in myfile:
    d = toolbox.datafile(fname)
    my_mood = d['var_one']
    number  = d['var_two']
    decimal = d['var_three']
    candy   = d['var_four']

And then printing my_mood would print out happy.

However, this toolbox is not python 3 compliant and I did not make it so I would like to know if there is an easy built in toolbox that can accomplish this task.

Thanks in advance

EDIT**

The importing method seems like it will be the most helpful for answering this question. The only problem that I have now with it is that I do not know how to import the files.

To explain further I am going to be parsing the command-line arguments and one of the arguments will be the location of said file that we want to import. What is the syntax to import that?

I have an args.file that equals <home/myname/python/myfile.py>

So how would I import args.file?

  • 1
    Is toolbox something that is an external library for you? – rajah9 Jul 09 '20 at 13:21
  • 2
    those above contents looks like just variable, you can save those things in a text file. python script can directly access it and save it in a dictionary. then you do the steps you want – Subbu VidyaSekar Jul 09 '20 at 13:21
  • @subbu How though? Please post an answer if you have one – wjandrea Jul 09 '20 at 13:22
  • @rajah yes I believe so. It was made by another person within the company and is quite extensive so I do not know how long it will take them to get it Python 3 compliant. – newtopython Jul 09 '20 at 13:23
  • @SubbuVidyaSekar I do not want to save them in .txt files as we have thousands of these .py files with these variables – newtopython Jul 09 '20 at 13:25
  • @wjandrea not exactly. Very close but I am missing one more piece and I am about to update my question – newtopython Jul 09 '20 at 13:51
  • @wjandrea I have updated my question with what is still unclear to me. Thanks! – newtopython Jul 09 '20 at 14:03
  • 1
    @newtopython See [How to import a module given the full path?](https://stackoverflow.com/q/67631/4518341) Although I think alaniwi's solution with `configparser` is a better solution. – wjandrea Jul 09 '20 at 14:06
  • In that question you linked to. What is the `module.name` in the first answer representative of? What would be my input? – newtopython Jul 09 '20 at 15:15

5 Answers5

6

You can do:

In vars.py

var_one = 'happy'
var_two = '2345'
var_three = '-24.24'
var_four = 'Chocolate'

In main.py

import vars

# hard coded attribute lookup
print(vars.var_one)  # prints 'happy'

# to get an attribute dynamically, use getattr
name = "var_three"
print(getattr(vars, name))  # prints '-24.24'

Further example where the import is also done dynamically:

In main.py

module_name = "vars"

module = __import__(module_name)   # imports vars.py to variable 'module'

var_name = "var_three"

print(getattr(module, var_name))  # prints '-24.24'

although for situations where even the name of the file containing variables is only known at run time, it might make more sense to use something like configparser:

In vars.ini:

[DEFAULT]
var_one = happy
var_two = 2345
var_three = -24.24
var_four = Chocolate

In main.py:

import configparser

filename = "vars.ini"
varname = "var_one"
section = "DEFAULT"

config = configparser.ConfigParser()

config.read(filename)

print(config.get(section, varname))  # prints 'happy'
alani
  • 12,573
  • 2
  • 13
  • 23
  • What do you mean by 'get the attribute dynamically'? What is the difference between these two methods – newtopython Jul 09 '20 at 13:32
  • 1
    @newtopython It might not always be convenient to have to put the attribute name directly into the source code. In the second example you have the name of the attribute stored in a string, which for example could have been read from a file or user input rather than in the source code, and you can still do the lookup. This gives you the same flexibility that you have with your dictionary lookup in the example in the question. – alani Jul 09 '20 at 13:34
  • 1
    @newtopython I've now added a further example for when it is not convenient to hard-code the `import vars` line either. – alani Jul 09 '20 at 13:41
  • How can I import the specific filenames? I will update my question to be more specific. – newtopython Jul 09 '20 at 13:49
  • 1
    @newtopython I have seen your comment now in the question with `args.file` and I think that the `__import__` solution here would work for that. But I have also added another possiblitity with ini files for you to consider. – alani Jul 09 '20 at 14:05
  • I am unfamiliar with ini files. How do I get args.file which is a path to a .py file into the form of .ini? – newtopython Jul 09 '20 at 14:16
  • @newtopython If you want to stick with `.py` files using user-supplied filenames, use `__import__` as suggested. The configparser stuff was just a suggestion for another approach, that _might_ be useful, but it sounds maybe not what you want. As you can see, the ini file is in a different format, and is essentially just for simple data types (strings, or numbers that you will convert from strings). – alani Jul 09 '20 at 14:22
  • Let us [continue this discussion in chat](https://chat.stackoverflow.com/rooms/217539/discussion-between-newtopython-and-alaniwi). – newtopython Jul 09 '20 at 14:35
2

You can use "import" to import both functions and variables that are defined in other scripts. If you have

var_one = 'happy'

In a file named myvariables.py, then you can write the following to get access to this variable in another file:

from myvariables import var_one
jtb
  • 461
  • 1
  • 8
  • 22
  • 1
    This would be great if I only had a few variables but there are many of them and I do not want to import all of them in this manner. This is good to know though! – newtopython Jul 09 '20 at 13:27
1

You can import the variables just like you would import functions from the other script.

import <yourscriptfile> (Without the .py extension)
<yourscriptfile>.varname1
<yourscriptfile>.varname2

and so on

Orel Fichman
  • 150
  • 6
  • 1
    This is similar to Joshua's answer and might work for my purposes! I'll try it and come back. – newtopython Jul 09 '20 at 13:29
  • 1
    No worries, and by the way, you can also do it the other way around. Say you want to define a variable for the other script, you can simply do .varname = whatever. This tricks comes in handy sometimes. :) – Orel Fichman Jul 09 '20 at 13:37
  • 1
    This is the same method everyone seems to be suggesting so I will likely go with that but I edited my question with a problem that I ran in to. – newtopython Jul 09 '20 at 13:58
0

You can import everything from the file using a starred expression:

from filename import *

print(var_one)
print(var_two)
print(var_three)
print(var_four)

Output:

happy
2345
-24.24
Chocolate
Red
  • 26,798
  • 7
  • 36
  • 58
0

With a file myfile.py, you can do:

with open('myfile.py') as file:
    exec(file.read())

The variables will than be assigned in your namespace. If you had a number of files, you could loop through like:

for script in ['myfile1.py1', 'myfile2.py', 'myfile3.py']:
     with open(script) as file:
         exec(file.read())
         my_mood = var_one
         number  = var_two
         decimal = var_three
         candy   = var_four

But you would have to do the processing on those variables within the loop else they by overwritten (or save them in some array for each file).

But note that generally people discourage using exec. I like the import methods better but maybe this is fine in this case? Would be happy for people to input why they would encourage or avoid this approach.

Tom
  • 8,310
  • 2
  • 16
  • 36