#1
  1. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jan 2010
    Posts
    14
    Rep Power
    0

    Solved : Return statement


    Hi

    I got the following code which does what I want except one thing, if I do :

    Code:
    r = dectohex(39784)
    print r
    The result is None ??
    It only works if I write print instead of return..

    Code:
    # IMPORTS
    import string
    
    # list of HEX to DEC correspondances
    correspondances = {10:'A', 11:'B', 12:'C', 13:'D', 14:'E', 15:'F'}
    
    # list hosting translated digits
    hnumb = []
    
    # convert function dec to hex
    def dectohex(x):
        mod = x%16
        if mod > 9:
            hdigit = correspondances.get(mod)
        else:
            hdigit = mod
    
        hnumb.append(hdigit)
    
        if x/16 == 0:
            result = ''.join(str(i) for i in hnumb)
            return result[::-1]
        else:
            dectohex(x/16)
    Could someone explain to me why ?

    Thank you
  2. #2
  3. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jul 2007
    Location
    Joensuu, Finland
    Posts
    438
    Rep Power
    67
    Originally Posted by chaying
    Code:
        if x/16 == 0:
            result = ''.join(str(i) for i in hnumb)
            return result[::-1]
        else:
            dectohex(x/16)
    Could someone explain to me why ?
    Because your “else” branch lacks a “return”.

    Your function is defective in many other ways as well. For example, since “hnumb” is not a local function, the result will be different if hnumb != [] to begin with. These kind of variables should all be local.
    My armada: openSUSE 13.1 (home desktop, home laptop), Crunchbang Linux 11 (work laptop), Trisquel GNU/Linux 6.0.1 (mini laptop), Ubuntu 14.04 LTS (server), Android 4.2.1 (tablet), Windows 7 Ultimate (testbed)
  4. #3
  5. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jan 2010
    Posts
    14
    Rep Power
    0
    Hi Oscar

    Thanks to stop by.

    Sorry but I don't undertstand : 'lack of a return statement' ? What do you mean ? If I put a return statement :
    Code:
    else:
            dectohex(x/16)
            return
    Wouldn't that be some 'dead code' : this code will never be reached, will it ?
    edit: after test, it doesn't change anything.

    And I modified my function inserting a :
    Code:
    global hnumb
    after the function definition but I don't see how it could be a local variable as it would be reinitialized each time, wouldn't it ?

    You said 'many ways', what other ways would you think about ?
  6. #4
  7. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jul 2007
    Location
    Joensuu, Finland
    Posts
    438
    Rep Power
    67
    Originally Posted by chaying
    Sorry but I don't undertstand : 'lack of a return statement' ? What do you mean ? If I put a return statement :
    Code:
    else:
            dectohex(x/16)
            return
    “return” without an argument is the same as “return None” which, incidentally, is also the default return value for a function without a return statement, so of course that doesn’t change anything.

    But what do you expect the line previous to that does? Put a return before the “dectohex(x/16)” so the function might ultimately actually return something.

    And I modified my function inserting a :
    Code:
    global hnumb
    after the function definition but I don't see how it could be a local variable as it would be reinitialized each time, wouldn't it ?
    True, if you let it, but it’s still bad practice for functions to modify outside environment.

    Edit: I might as well add this as an afterthought... One way to get rid of global variables is to use an optional function parameter:

    Code:
    def dectohex(x, hnumb=None):
        # ...
        if hnumb is None:
            hnumb = []
        hnumb.append(hdigit)
        if x // 16 == 0:
            return ''.join([str(i) for i in hnumb])[::-1]
        else:
            return dectohex(x // 16, hnumb)
    Last edited by SuperOscar; January 29th, 2013 at 04:10 AM.
    My armada: openSUSE 13.1 (home desktop, home laptop), Crunchbang Linux 11 (work laptop), Trisquel GNU/Linux 6.0.1 (mini laptop), Ubuntu 14.04 LTS (server), Android 4.2.1 (tablet), Windows 7 Ultimate (testbed)
  8. #5
  9. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jan 2010
    Posts
    14
    Rep Power
    0
    “return” without an argument is the same as “return None” which, incidentally, is also the default return value for a function without a return statement, so of course that doesn’t change anything.
    Ok, my bad..

    But what do you expect the line previous to that does? Put a return before the “dectohex(x/16)” so the function might ultimately actually return something.
    It's actually a real misunderstanding of the flow of execution here..
    I really didn't see why with the initial statement, the function doesn't end systematically on the return from the if statement.

    My understanding now is that without the return statement, it's like I call a new function wich does the same thing but that isn't related to any previous calculation : it looks like it's recursive but it's not. Am I right ?

    One way to get rid of global variables is to use an optional function parameter:
    Code:
    def dectohex(x, hnumb=None):
        # ...
        if hnumb is None:
            hnumb = []
        hnumb.append(hdigit)
        if x // 16 == 0:
            return ''.join([str(i) for i in hnumb])[::-1]
        else:
            return dectohex(x // 16, hnumb)
    Thanks a lot for the tip and your help !
  10. #6
  11. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jul 2007
    Location
    Joensuu, Finland
    Posts
    438
    Rep Power
    67
    Originally Posted by chaying
    My understanding now is that without the return statement, it's like I call a new function wich does the same thing but that isn't related to any previous calculation : it looks like it's recursive but it's not. Am I right ?
    It’s recursive all right. The main point is what happens after the recursive call is ended and the execution returns to the caller. In your code, the value obtained would simply be discarded. Adding the “return” makes the function ultimately have some end result.
    My armada: openSUSE 13.1 (home desktop, home laptop), Crunchbang Linux 11 (work laptop), Trisquel GNU/Linux 6.0.1 (mini laptop), Ubuntu 14.04 LTS (server), Android 4.2.1 (tablet), Windows 7 Ultimate (testbed)
  12. #7
  13. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jan 2010
    Posts
    14
    Rep Power
    0
    Ok I think I get it now..

    I'm still going to run some flows to be sure but so, the ultimate 'return' that I thought would get me the result, only returns it to the last calling function, which holds the result until someone says to her to return it, or that the system discards it : what I didn't do.

    I hope I get it right now.. If not, please keep in mind that I do "help 'my' landlady to take out her garbage"..

    Thanks again anyway !
  14. #8
  15. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jul 2007
    Location
    Joensuu, Finland
    Posts
    438
    Rep Power
    67
    Originally Posted by chaying
    Ok I think I get it now..
    No need to call the landlady, you got it right
    My armada: openSUSE 13.1 (home desktop, home laptop), Crunchbang Linux 11 (work laptop), Trisquel GNU/Linux 6.0.1 (mini laptop), Ubuntu 14.04 LTS (server), Android 4.2.1 (tablet), Windows 7 Ultimate (testbed)

IMN logo majestic logo threadwatch logo seochat tools logo