Ok, let me try to explain some images.
In Python, everything is an object. These objects refer to variables. Some kinds of objects, such as lists and tuples, simply store links to other objects.
However, when you perform
myVar = ["jhhj", "hgc"] myTuple = ([1,2,3], [4,5,6], myVar)
You get more or less this scenario:

Each object is represented by a rectangle / rectangle. We have two string objects, "jhhj" and "hgc" . In addition, we have a list object indicated by the variable myVar ; this list object points to both string objects. In addition, we have a tuple object referenced by myTuple ; this tuple object points to two other lists and the list referenced by myVar .
While doing
myVar.append('lololol')
what's happening? Well, the list object (which, incidentally, points to myVar ) starts to refer to another value, the string object "lololol" :

Note that myVar is still referencing a list object. It so happened that the list object has changed. You can look at this list object from both myVar and the tuple, you will see the same object with the same change.
OTOH when you perform
myVar = "lol" myTuple = ([1,2,3], [4,5,6], myVar)
You will get something like this:

Now myVar points to the string object "lol" , and the tuple refers to its third position. Now if you follow
myVar = "lolol"
you just force myVar to point to another object. The tuple object still points to "lol" as before:

So, if you assign a new value to a variable, it will simply change the value indicated by that variable. The previous value referenced by the variable will still be *, and any other variable or object pointing to it will remain pointed to it. Only the attribute variable is changed.
PS: In addition, I answered a somewhat vague question some time ago . You may find the answer helpful.
* Except for garbage collection, but this is another long story.