I'm having issues trying to pass an empty parameter can someone explain to me why my code isn't working. I have a math test file that goes through my math library file but my lib file can't read the () code. When I run the code it says init() missing 1 required positional argument: 'y'
import MathLib as math
math test:
if __name__ == '__main__':
math_obj1 = math.MyMathLib(2.0)
math_obj2 = math.MyMathLib(-0.5)
math_obj3 = math.MyMathLib() # this should give 0.0
print("Math obj1 value = ",math_obj1.get_curr_value() )
print("Math obj2 value = ",math_obj2.get_curr_value() )
print("Math obj3 value = ",math_obj3.get_curr_value() )
import math
class MyMathLib:
def __init__(self, y,):
self.y = y
if self == None:
value == 0.0
As posted, your definition of the __init__() function has y as a required argument.
If you want it to be optional and have a default value of zero, then write it this way:
class MyMathLib:
def __init__(self, y=0.0):
The self variable isn't actually a passable parameter in class methods (I recommend you take another look at python classes). The first (and only) passable parameter in your init function is y. Since y has no default variable, you must pass a value for y, or give it a default value:
def __init__(self, y=0.0):
self.y = y
Also I'm not sure what you're trying to achieve with this line, it makes no sense:
if self == None:
value == 0.0
value is only local to the init function, maybe you meant self.value? Even then, self will never be None (unless you assign self = None within the method), so the statement will never trigger. Ontop of that, you've used a double == instead of =.
You have to set default value in __init__
def __init__(self, y=0.0):
self.y = y
and then you don't have to check None
Or using None
def __init__(self, y=None):
self.y = y
if self.y is None:
self.y = 0.0
It can be useful if you want to recognize if someone used MyMathLib() or MyMathLib(0.0)
That is because your __init__ requires two arguments instead of one. Instead of doing this, you can pass a default variable like #Jay Mody's answer. And also:
self == None will never be true because self always passes in a value y.
Here is another way you can do it:
class MyMathLib:
def __init__(self):
self.y = 0.0
def passNumber(y):
self.y = y
As you can see, if the number is passed using passNumber, that means that the number isn't 0.0. This is another way to do it.
Related
Currently I have 2 global variables within my python module. I wanted to get away from using the global variable scope, while still being able to call the 2 variables throughout my module. Basically what's the best way to get away from the global object, while still being able to validate arguments.
I tried creating a class within a function, which i realized wouldnt work.
global gl_args
global gl_hashType
gl_args 1⁄4 parser.parse_args()
if gl_args.md5:
gl_hashType = 'MD5'
elif gl_args.sha256:
gl_hashType = 'SHA256'
elif gl_args.sha512:
gl_hashType = 'SHA512'
elif gl_args.sha224:
gl_hashType = 'SHA224'
elif gl_args.sha384:
gl_hashType = 'SHA384'
else:
gl_hashType = "Unknown"
logging.error('Unknown Hash Type Specified')
DisplayMessage("Command line processed: Successfully")
return
this is only one piece of where it is used but the 2 variables are used throughout the program.
Calling the variable throughout the module.
Sounds like you want a class
class MyClass(object):
def __init__(self,x,y):
self.x = x
self.y = y
def f1(self):
return self.x + self.y
def f2(self):
return self.y - self.x
def area(self):
return self.y*self.x
used like this:
my_instance = MyClass(4,5)
my_instance.f1()
my_instance.f2()
I want to create a function within a class that can access two different members with the same function. For example in the code below, I want both of the lines below to use the 'apply' function on different variables in the class
print(state.apply(rate))
print(state.apply(wage))
I had thought if I put in a dummy variable in the function definition (called exposure), it would replace it with the variables passed to the function (rate and wage in the example below). What is the correct way of doing this in python 3?
class State():
def __init__(self):
self.rate = 0
self.wage = 0
def apply(self, exposure):
self.exposure = self.exposure - 1
return self.exposure
state = State()
rate = State.rate
wage = State.wage
print(state.apply(rate))
print(state.apply(wage))
EDIT: I had made a typo where I had State instead of state in each print statement. I have now corrected this
This would be the only way:
class State:
def __init__ (self):
self.rate = 0
self.wage = 0
def apply (self, exposure):
setattr(self, exposure, getattr(self, exposure) - 1)
return getattr(self, exposure)
>>> state = State()
>>> print(state.apply('rate'))
-1
>>> print(state.apply('wage'))
-1
>>> print(state.apply('wage'))
-2
Note that those are instance variables, so you cannot access them using the type, State, but only using the object, state.
However, I would say, that whatever you are trying, you’re doing it wrong. If you describe your actual problem, we may be able to suggest a way better solution for it instead.
I'm trying to make a robotics kit. Its designed to be simple so I'm using properties so when the users change a parameter the property method sends the serial command which controls motors/ servos/whatever.
This is the code at the moment, directly from a previous question I asked on here.
class Servo(object):
def __init__(self, which_servo, angle = 0):
self._angle = angle;
self._servo_no = which_servo
def get_angle(self):
return self._angle
def set_angle(self, value):
self._angle = value
print "replace this print statement with the code to set servo, notice that this method knows the servo number AND the desired value"
def del_angle(self):
del self._angle
angle = property(get_angle, set_angle, del_angle, "I'm the 'angle' property.
this is then initialized as such:
class robot(object):
def __init___(self):
self.servos = [Servo(0), Servo(1), Servo(2), Servo(3)]
Now, this works in the respect that it does change the variable through the getter and setter functions, however the prints in the getter and setter never is printed, thus if I replace it with a serial command I assume it won't do anything either, can anyone shed any light on this?
Thanks
Update: Thanks for the help using the servo file this is whats happened, there are three scenarios the first works and by extension I would have assumed the next two preferable scenarios would work but they don't any ideas?
This works
import servo
class Robot(object):
def __init__(self):
self.servos = [servo.Servo(0, 0), servo.Servo(1,0), servo.Servo(2,0)]
R = Robot()
R.servos[1].angle = 25
This does not:
import servo
class Robot(object):
def __init__(self):
self.servos = [servo.Servo(0, 0), servo.Servo(1,0), servo.Servo(2,0)]
R = Robot()
left_servo = R.servos[1].angle
left_servo = 25
Neither does this
import servo
class Robot(object):
def __init__(self):
self.servos = [servo.Servo(0, 0).angle, servo.Servo(1,0).angle, servo.Servo(2,0).angle]
R = Robot()
R.servo[1] = 25
Using the preferred decorator syntax for properties, this works fine. It'll also help you avoid issues like this in the future
class Servo(object):
def __init__(self, which_servo, angle = 0):
self._angle = angle;
self._servo_no = which_servo
#property
def angle(self):
return self._angle
#angle.setter
def angle(self, value):
self._angle = value
print "replace this print statement with the code to set servo"
#angle.deleter
def angle(self):
del self._angle
Seeing as your indentation is off here, I believe this is likely an issue of indentation in your source. This should work as well if you really want to use the old property function:
class Servo(object):
def __init__(self, which_servo, angle = 0):
self._angle = angle;
self._servo_no = which_servo
def get_angle(self):
return self._angle
def set_angle(self, value):
self._angle = value
print "replace this print statement with the code to set servo"
def del_angle(self):
del self._angle
angle = property(get_angle, set_angle, del_angle,"I'm the 'angle' property.")
Both of these work successfully for me (inside a file called servo.py)
>>> import servo
>>> s = servo.Servo(1, 2)
>>> s.angle
2
>>> s.angle = 3
replace this print statement with the code to set servo
EDIT
To address your new issues. When you assign R.servos[1].angle to left_servo, its not creating a reference to the servos angle, it's just setting left_servo to whatever the angle is. When you reassign 25 to it, you're not assigning to the angle you're assigning to the left_servo.
On the second one, I'm assuming you meant R.servos and not R.servo which should be raising an AttributeError. But the real problem as I see it, is you should be saying R.servos[1].angle = 25 and you're omitting the .angle.
To (attempt to) put it simply: When you use the = operator, you are changing where a name refers to, not what it refers to.
>>> x = 1
>>> x = 2
the second assignment does not overwrite the 1 in memory with a 2, it just changes where x refers to. So if I did something like
>>> x = 1
>>> y = x
>>> y = 2
>>> print x
1
the output is 1 because your are telling y to refer to the same place that x refers. Changing y to 2 changes where y refers to, it does not change the 1 already in memory.
I am trying to simply get the value out of my class using a simple function with a return value, I'm sure its a trivial error, but im pretty new to python
I have a simply class set up like this:
class score():
#initialize the score info
def __init__(self):
self.score = 0
self.num_enemies = 5
self.num_lives = 3
# Score Info
def setScore(num):
self.score = num
# Enemy Info
def getEnemies():
return self.num_enemies
# Lives Info
def getLives():
return self.getLives
etc.....
Than I create an instance of the class as such:
scoreObj = score()
for enemies in range(0, scoreObj.getEnemies):
enemy_sprite.add(enemy())
I get the error saying that an integer is expected, but it got an instancemethod
What is the correct way to get this information?
Thanks!
scoreObj.getEnemies is a reference to the method. If you want to call it you need parentheses: scoreObj.getEnemies().
You should think about why you are using a method for this instead of just reading self.num_enemies directly. There is no need for trivial getter/setter methods like this in Python.
The first parameter for a member function in python is a reference back to the Object.
Traditionally you call it "self", but no matter what you call the first parameter, it refers back to the "self" object:
Anytime I get weird errors about the type of a parameter in python, I check to see if I forgot the self param. Been bit by this bug a few times.
class score():
#initialize the score info
def __init__(self):
self.score = 0
self.num_enemies = 5
self.num_lives = 3
# Score Info
def setScore(self, num):
self.score = num
# Enemy Info
def getEnemies(self):
return self.num_enemies
# Lives Info
def getLives(foo): #foo is still the same object as self!!
return foo.num_lives
#Works but don't do this because it is confusing
This code works:
class score():
def __init__(self):
self.score = 0
self.num_enemies = 5
self.num_lives = 3
def setScore(self, num):
self.score = num
def getEnemies(self):
return self.num_enemies
def getLives(self):
return self.getLives
scoreObj = score()
for enemy_num in range(0, scoreObj.getEnemies()):
print enemy_num
# I don't know what enemy_sprite is, but
# I commented it out and just print the enemy_num result.
# enemy_sprite.add(enemy())
Lesson Learned:
Class functions must always take one parameter, self.
That's because when you call a function within the class, you always call it with the class name as the calling object, such as:
scoreObj = score()
scoreObj.getEnemies()
Where x is the class object, which will be passed to getEnemies() as the root object, meaning the first parameter sent to the class.
Secondly, when calling functions within a class (or at all), always end with () since that's the definition of calling something in Python.
Then, ask yourself, "Why am I not fetching 'scoreObj.num_lives' just like so instead? Am I saving processing power?" Do as you choose, but it would go faster if you get the values directly from the class object, unless you want to calculate stuff at the same time. Then your logic makes perfect sense!
You made a simple mistake:
scoreObj.getEnemies()
getEnemies is a function, so call it like any other function scoreObj.getEnemies()
I have a method that i have broken into smaller nested functions to break up the code base:
def foo(x,y):
def do_this(x,y):
pass
def do_that(x,y):
pass
do_this(x,y)
do_that(x,y)
return
Is there a way to run one of the nested functions by itself. eg:
foo.do_this(x,y)
EDIT:
I am trying to setup caching on a web server i have built using pyramid_breaker
def getThis(request):
def invalidate_data(getData,'long_term',search_term):
region_invalidate(getData,'long_term',search_term)
#cached_region('long_term')
def getData(search_term):
return response
search_term = request.matchdict['searchterm']
return getData(search_term)
This is my understanding may not be accurate:
Now the reason i have this is that the namespace used by the decorator to create the cache key is genereated from the function and the arguements. You can't therefore just put the decorator on getThis as the request variable is unique-ish and the cache is useless. So i created the inner function which has repeatable args (search_term).
However to invalidate the cache (ie refresh), the invalidation function requires scope to know of the 'getData' function so also needs to be nested. Therefore i need to call the nested function. You wonderful people have made it clear its not possible so is someone able to explain how i might do it with a different structure?
I assume do_this and do_that are actually dependent on some argument of foo, since otherwise you could just move them out of foo and call them directly.
I suggest reworking the whole thing as a class. Something like this:
class Foo(object):
def __init__(self, x, y):
self.x = x
self.y = y
def do_this(self):
pass
def do_that(self):
pass
def __call__(self):
self.do_this()
self.do_that()
foo = Foo(x, y)
foo()
foo.do_this()
These previous answers, telling you that you can not do this, are of course wrong.
This is python, you can do almost anything you want using some magic code magic.
We can take the first constant out of foo's function code, this will be the do_this function. We can then use this code to create a new function with it.
see https://docs.python.org/2/library/new.html for more info on new and https://docs.python.org/2/library/inspect.html for more info on how to get to internal code.
Warning: it's not because you CAN do this that you SHOULD do this,
rethinking the way you have your functions structured is the way to go, but if you want a quick and dirty hack that will probably break in the future, here you go:
import new
myfoo = new.function(foo.func_code.co_consts[1],{})
myfoo(x,y) # hooray we have a new function that does what I want
UPDATE: in python3 you can use the types module with foo.__code__:
import types
myfoo = types.FunctionType(foo.__code__.co_consts[1], {})
myfoo() # behaves like it is do_this()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: do_this() missing 2 required positional arguments: 'x' and 'y'
There is, you have to make them as an attribute of the function object. But this will work only after the first call of foo.
def foo(x,y):
def do_this(x,y):
pass
def do_that(x,y):
pass
do_this(x,y)
do_that(x,y)
foo.do_this = do_this
foo.do_that = do_that
return
>>> foo.do_this(1, 2)
AttributeError: 'function' object has no attribute 'do_this'
>>> foo(1, 2)
>>> foo.do_this(1, 2)
>>>
No (apart from poking around in closure objects, which is complete overkill here). If you need that, use a class.
class foo(object):
def do_this(self, x, y):
...
def do_that(self, x, y):
...
def do_other_stuff(self, x, y):
# or __call__, possibly
Or just put those functions in the outer scope, since you're passing everything as arguments anyway:
def foo(x, y):
do_this(x, y)
do_that(x, y)
def do_this(x, y):
...
def do_that(x, y):
...
No, there is not. Since you may access variables in an outer scope from within a nested function:
def foo(x,y):
def do_this(z):
print(x,y,z)
# ...
there is no way to call do_this while providing a binding for x and y.
If you must call do_this from elsewhere, simply make it a top level function at the same level as foo.
You can try this way:
def a(x, y):
name = 'Michael'
a.name = name
a.z = z = x * y
#a.z = z
def b():
def give_me_price(f,g):
price = f * g
return price
def two(j,k):
surname = 'Jordan' # without return surname give None
# two = two('arg1', 'arg2')
# b.blabla = two
one = give_me_price(5, 10)
b.halabala = one
print(a.name) # ;)
x = 20
y = 30
a(x,y) # IMPORTANT! first you must run function
print(a.z)
print(a.name * 5)
print('-'*12)
b() # IMPORTANT! first you must run function
print('price is: ' + str(b.give_me_price(5, 25)))
# print(b.blabla)
This is how I did it.
CODE
def getMessage(a="", b="", c=""):
def getErrorMessage(aa, bb):
return "Error Message with/without params: {}{}".format(aa, bb)
def getSuccessMessage(bb, cc):
return "Success Message with/without params: {}{}".format(bb, cc)
def getWarningMessage(aa, cc):
return "Warning Message with/without params: {}{}".format(aa, cc)
return {
"getErrorMessage": getErrorMessage(a, b),
"getSuccessMessage": getSuccessMessage(b, c),
"getWarningMessage": getWarningMessage(a, c),
}
a = "hello"
b = " World"
c = "!"
print(getMessage(a, b)["getErrorMessage"])
print(getMessage(b=b, c=c)["getSuccessMessage"])
print(getMessage(a=a, c=c)["getWarningMessage"])
print(getMessage(c=c)["getWarningMessage"])
OUTPUT
Error Message with/without params: hello World
Success Message with/without params: World!
Warning Message with/without params: hello!
Warning Message with/without params: !