I have a nested function such that
def f(l):
def g(index):
print index
l.apply(lambda x :x if x else g(x.name))
g(index) is an internal function of f(x). l is a 'pandas.core.series.Series' object which contains sets
>>> linked_on
1 set([xyz.com])
3 set([])
Name: EMAIL_ID, dtype: object
It seems like the internal function is not being recognized by the program and it just flows through in the else case without affecting anything. What I want is for the apply to call the internal function on the value if the set is empty. I put a breakpoint in the function but it never goes into it. When I try to break outside and run the function in the interpreter I get
NameError: global name 'g' is not defined
But I never get this error while running the code as is and it just flows through without giving any errors but also not going into the internal function. Any help into explaining this phenomenon will be greatly appreciated
Related
def prefix_factory(prefix):
def prefix_printer(text):
print(f"{prefix}: {text}")
return prefix_printer
Now lets execute the below line.
# First time we are executing this
debug = prefix_factory('DEBUG')
# Second time we are executing as
debug('Hello world')
First time we are executing this
1st execution or assignment of function to the variable debug is assigned the value "DEBUG". My understanding is this is how it has to be executed.
ideally inner function prefix_printer(text) - gets defined inside prefix_factory()
'return prefix_printer' should get an error, stating that text is not available or text is missing.
Second time we are executing as
debug('hello world ') - 2nd execution of the function reference.
The question for the second execution is, I am assuming 'hello world' should be considered as a value for the prefix. and text should be blank as we don't call prefix_printer in the return statement with any value. Hence it has to be '' empty string. I am coming from c, C++ background.
My question is, it's the same piece of code 1st-time prefix is assigned,
but during the 2nd execution debug('Hello world') it behaves differently. How is it possible, please clarify in detail how this works?
When debug = prefix_factory('DEBUG') is executed, variable debug is assigned the return value from calling function prefix_factory('DEBUG'). It is not assigned the value "DEBUG" as you said. And what is this return value?
Function prefix_factory returns prefix_printer, which is a function nested within prefix_factory. Moreover, prefix_printer references a variable, prefix, which is defined in the outer, enclosing function. When prefix_factory returns a nested function, prefix_printer, that references a variable defined in the nesting function, that returned function is known as a closure. Even though we have now returned from the call to printing_factory, the closure function prefix_printer, which has now been assigned to variable debug, still has a reference to the value of variable prefix as it existed at the time prefix_factory was called.
Subsequently, when you execute debug('Hello World'), because debug evaluates to our prefix_printer closure , this is equivalent to calling function prefix_printer('Hello World') with variable prefix initialized to 'DEBUG'.
I know there are quite a few "python scope questions" here but I am VERY rusty with python and I am really confused about a "UnboundLocalError" problem I keep getting. I have read that 'for' loops do not have a contained scope yet my code seems to be acting in that way... My code looks like this:
`
...
for b in blocks[:]:
if b.contains(CONSTANT_NUM):
r = b.split(CONSTANT_NUM+2)
if r: blocks.append(r)
Foo= struct.unpack('<H', b.data)[0]
Bar = Foo
...
print("Foo: 0x%x" % (Foo))
`
Whenever I run this, I get the error "UnboundLocalError: local variable 'Foo' referenced before assignment". When I instead try and print Bar I get the same error. Why is the assignment not being carried outside of the 'for' loop?
It could be very likely that your loop never went into the if statement and hence Foo was never initialized.
You need to initialize it before the loop just to make sure that if that conditional is never met, you have something to print.
In your case, if the 1st if condition is failing, then the compiler won't reach the Foo = ... statement. Which will result in the error you are getting now.
The error indicates that at the time of checking the variable foo you have not yet initialized.
you should initialize it before the loop.
True or False
If a function is defined but never called, then Python automatically detects that and issues a warning
One of the issues with this is that functions in Python are first class objects. So their name can be reassigned. For example:
def myfunc():
pass
a = myfunc
myfunc = 42
a()
We also have closures, where a function is returned by another function and the original name goes out of scope.
Unfortunately it is also perfectly legal to define a function with the same name as an existing one. For example:
def myfunc(): # <<< This code is never called
pass
def myfunc():
pass
myfunc()
So any tracking must include the function's id, not just its name - although that won't help with closures, since the id could get reused. It also won't help if the __name__ attribute of the function is reassigned.
You could track function calls using a decorator. Here I have used the name and the id - the id on its own would not be readable.
import functools
globalDict = {}
def tracecall(f):
#functools.wraps(f)
def wrapper(*args, **kwargs):
global globalDict
key = "%s (%d)" % (f.__name__, id(f))
# Count the number of calls
if key in globalDict:
globalDict[key] += 1
else:
globalDict[key] = 1
return f(*args, **kwargs)
return wrapper
#tracecall
def myfunc1():
pass
myfunc1()
myfunc1()
#tracecall
def myfunc1():
pass
a = myfunc1
myfunc1 = 42
a()
print(globalDict)
Gives:
{'myfunc1 (4339565296)': 2, 'myfunc1 (4339565704)': 1}
But that only gives the functions that have been called, not those that have not!
So where to go from here? I hope you can see that the task is quite difficult given the dynamic nature of python. But I hope the decorator I show above could at least allow you to diagnose the way the code is used.
No it is not. Python is not detect this. If you want to detect which functions are called or not during the run time you can use global set in your program. Inside each function add function name to set. Later you can print your set content and check if the the function is called or not.
False. Ignoring the difficulty and overhead of doing this, there's no reason why it would be useful.
A function that is defined in a module (i.e. a Python file) but not called elsewhere in that module might be called from a different module, so that doesn't deserve a warning.
If Python were to analyse all modules that get run over the course of a program, and print a warning about functions that were not called, it may be that a function was not called because of the input in this particular run e.g. perhaps in a calculator program there is a "multiply" function but the user only asked to sum some numbers.
If Python were to analyse all modules that make up a program and note and print a warning about functions that could not possibly be called (this is impossible but stay with me here) then it would warn about functions that were intended for use in other programs. E.g. if you have two calculator programs, a simple one and an advanced one, maybe you have a central calc.py with utility functions, and then advanced functions like exp and log could not possibly be called when that's used as part of simple program, but that shouldn't cause a warning because they're needed for the advanced program.
So, I was working on some code trying to resolve a bug. This was the original chunk of code:
passrate = 90
for child in sorted_children:
if child.passrate >= passrate:
return child
return None
This code was buggy and this is it's fix:
passrate = 90
for child in sorted_children:
if child.passrate() >= passrate:
return child
return None
The only difference is the added parenthesis. So, child is a class and passrate() is it's method which lazy-loads and returns it's __passrate value. If it's not calculated yet, it calculates it before returning it.
When I used the debugger to see what was causing the problem, I saw that sometimes when passrate() was executing it was like code execution somehow ended up in a completely wrong instance of child's class.
I know that without the parenthesis a pointer to the function is returned, but as it's done inside a logical operation, the function should be executed immediately afterwards so the final result should be the same for both chunks of code. And sometimes it indeed was. But sometimes it wasn't for some reason, always in the same iterated child in every execution of the code.
If someone could explain what could have caused the problem, I'd appreciate it very much.
EDIT:
Thanks everyone for helping. The old code was clearly wrong. I have no idea how it worked at all in the past.
I think, as per python's rule if it's method, then it should be called with braces. If it's a property then you can call without braces as below:
class Hello(object):
#property
def hi(self):
print "hello"
def hifunc(self):
print "Hi function"
h=Hello()
print h.hi
print h.hifunc
print h.hifunc()
Output:
hello
None
<bound method Hello.hifunc of <__main__.Hello object at 0x0000000002B99358>>
Hi function
None
None is printed as my example function returns nothing. In your case, when you call with braces, your return values from function used for comparison.
I have been working at learning Python over the last week and it has been going really well, however I have now been introduced to custom functions and I sort of hit a wall. While I understand the basics of it, such as:
def helloworld():
print("Hello World!")
helloworld()
I know this will print "Hello World!".
However, when it comes to getting information from one function to another, I find that confusing. ie: function1 and function2 have to work together to perform a task. Also, when to use the return command.
Lastly, when I have a list or a dictionary inside of a function. I'll make something up just as an example.
def my_function():
my_dict = {"Key1":Value1,
"Key2":Value2,
"Key3":Value3,
"Key4":Value4,}
How would I access the key/value and be able to change them from outside of the function? ie: If I had a program that let you input/output player stats or a character attributes in a video game.
I understand bits and pieces of this, it just confuses me when they have different functions calling on each other.
Also, since this was my first encounter with the custom functions. Is this really ambitious to pursue and this could be the reason for all of my confusion? Since this is the most complex program I have seen yet.
Functions in python can be both, a regular procedure and a function with a return value. Actually, every Python's function will return a value, which might be None.
If a return statement is not present, then your function will be executed completely and leave normally following the code flow, yielding None as a return value.
def foo():
pass
foo() == None
>>> True
If you have a return statement inside your function. The return value will be the return value of the expression following it. For example you may have return None and you'll be explicitly returning None. You can also have return without anything else and there you'll be implicitly returning None, or, you can have return 3 and you'll be returning value 3. This may grow in complexity.
def foo():
print('hello')
return
print('world')
foo()
>>>'hello'
def add(a,b):
return a + b
add(3,4)
>>>7
If you want a dictionary (or any object) you created inside a function, just return it:
def my_function():
my_dict = {"Key1":Value1,
"Key2":Value2,
"Key3":Value3,
"Key4":Value4,}
return my_dict
d = my_function()
d['Key1']
>>> Value1
Those are the basics of function calling. There's even more. There are functions that return functions (also treated as decorators. You can even return multiple values (not really, you'll be just returning a tuple) and a lot a fun stuff :)
def two_values():
return 3,4
a,b = two_values()
print(a)
>>>3
print(b)
>>>4
Hope this helps!
The primary way to pass information between functions is with arguments and return values. Functions can't see each other's variables. You might think that after
def my_function():
my_dict = {"Key1":Value1,
"Key2":Value2,
"Key3":Value3,
"Key4":Value4,}
my_function()
my_dict would have a value that other functions would be able to see, but it turns out that's a really brittle way to design a language. Every time you call my_function, my_dict would lose its old value, even if you were still using it. Also, you'd have to know all the names used by every function in the system when picking the names to use when writing a new function, and the whole thing would rapidly become unmanageable. Python doesn't work that way; I can't think of any languages that do.
Instead, if a function needs to make information available to its caller, return the thing its caller needs to see:
def my_function():
return {"Key1":"Value1",
"Key2":"Value2",
"Key3":"Value3",
"Key4":"Value4",}
print(my_function()['Key1']) # Prints Value1
Note that a function ends when its execution hits a return statement (even if it's in the middle of a loop); you can't execute one return now, one return later, keep going, and return two things when you hit the end of the function. If you want to do that, keep a list of things you want to return and return the list when you're done.
You send information into and out of functions with arguments and return values, respectively. This function, for example:
def square(number):
"""Return the square of a number."""
return number * number
... recieves information through the number argument, and sends information back with the return ... statement. You can use it like this:
>>> x = square(7)
>>> print(x)
49
As you can see, we passed the value 7 to the function, and it returned the value 49 (which we stored in the variable x).
Now, lets say we have another function:
def halve(number):
"""Return half of a number."""
return number / 2.0
We can send information between two functions in a couple of different ways.
Use a temporary variable:
>>> tmp = square(6)
>>> halve(tmp)
18.0
use the first function directly as an argument to the second:
>>> halve(square(8))
32.0
Which of those you use will depend partly on personal taste, and partly on how complicated the thing you're trying to do is.
Even though they have the same name, the number variables inside square() and halve() are completely separate from each other, and they're invisible outside those functions:
>>> number
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
NameError: name 'number' is not defined
So, it's actually impossible to "see" the variable my_dict in your example function. What you would normally do is something like this:
def my_function(my_dict):
# do something with my_dict
return my_dict
... and define my_dict outside the function.
(It's actually a little bit more complicated than that - dict objects are mutable (which just means they can change), so often you don't actually need to return them. However, for the time being it's probably best to get used to returning everything, just to be safe).