Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
180 views
in Technique[技术] by (71.8m points)

python - Pythonic way to change the value of something passed into a function, and have that change persist outside the function

I sometimes want to pass an object to a function, and have that function change the value of the original object. If I was using C++ I would pass by reference. What are the different ways I could do this in python, what is the recommended way, and why isn't there a simple way (like passing by reference in C++) to do this?

To demonstrate:

from enum import IntEnum

class Bar(IntEnum):
    A=0
    B=1
    C=2

def mutate(b: Bar):
    b = Bar.B # b is immutable. It does not change the value of the b parameter, instead it rebinds, and becomes a new Bar.B

if __name__ == '__main__':
    b=Bar.A
    print(b) # prints Bar.A
    mutate(b)
    print(b) # still prints Bar.A

In this example, you might expect the second print(b) to output Bar.B, but instead, it remains Bar.A, because the mutate function is essentially saying "b can forget about what it used to be bound to, and instead it is now bound to this Bar.A".

If b was a list or another mutable type, you could still append to it and that change would persist outside of the function because lists are mutable.

But what am I supposed to do if I want to change the value of an immutable type from within a function and have that change persist outside of the function?

One solution is to wrap it in a class because classes are mutable:

from enum import IntEnum
from typing import Generic, TypeVar

class Bar(IntEnum):
    A=0
    B=1
    C=2

T=TypeVar('T')
class Mutable(Generic[T]):
    def __init__(self, data: T):
        self.data = data

def mutate(b: Mutable[Bar]):
    b.data = Bar.B # b is mutable. The change to the b parameter will persist outside of this function

if __name__ == '__main__':
    b=Mutable(Bar.A)
    print(b.data) # prints Bar.A
    mutate(b)
    print(b.data) # prints Bar.B

But something tells me that if this was a good idea, then it would already be in the python standard library. So why isn't this a good idea? And what is the recommended way to get the behaviour that I want?

Thanks!


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)
等待大神答复

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...