-1

currentNode is a linked list I created, the nodes are 1, 2, 3.

def transformRecursive(lst):
    if lst == None:
        return
    else:
        return [lst.value].append(transformRecursive(lst.nextNode))

print(transformRecursive(currentNode))

The output only gives me None Instead of ["1","2","3"].

  • 5
    `append()` returns None in python. You are appending to the list, but you're not returning the list. You might try: `return [lst.value] + transformRecursive(lst.nextNode)` – Mark Apr 29 '21 at 23:40
  • [lst.value] + transformRecursive(lst.nextNode) would report builtins.TypeError: can only concatenate list (not "NoneType") to list. I think there is something wrong with my base case – Tianyu Wang Apr 30 '21 at 00:16
  • There are some basics it seems @TianyuWang needs some info on, I tried to provide an answer that helps explain a few basics in addition to providing a working solution. However, it would help to know exactly what `lst` is --> a list? node? linked list? etc. – Aelarion Apr 30 '21 at 00:31
  • @TianyuWang, perhaps your base case should be an empty list. That would make sense to me as the analog of an empty linked-list. – Mark Apr 30 '21 at 00:41
  • You should try print(lst) after the first if and also print lst after the Else (before returning) to help yourself debug. – PKCS12 Apr 30 '21 at 08:01

1 Answers1

0

Some quick explanations:

For your transformRecursive function, what it appears you're trying to do is generate a single list of all linked "node" values. From what you have in transformRecursive, even if this behaved as you expected you would actually end up with something like ["1", ["2",["3"]]] instead of ["1","2","3"].

From the Python docs, when you use append on a list, it is equivalent to myList[len(myList):] = [x] (where myList is the list in question, and x is the item to be appended). Given the above explanation, what I think you actually might want to use here is extend(x) (which has the same behavior, e.g. it returns None).

Secondly, as @Mark mentioned, list.append(x) returns None. So you can't use this as an assignment or return value. It is meant to be called "in place" to change the given list. Example:

# Example 1
myList = [1].append([2])
print(f"Example 1: {myList}")

# Example 2
myList = [1]
myList.append([2])
print(f"Example 2: {myList}")

# Example 3
myList = [1]
myList.append(2)
print(f"Example 3: {myList}")

Output:

Example 1: None
Example 2: [1, [2]]
Example 3: [1, 2]

Mutability:

I'm a little fuzzy on what lst actually is in your transformRecursive function, but I've mocked up a simple Node class to mimic what I think might be close enough for demonstration:

class Node:
    def __init__(self, value = None):
        self.value = value
        self.nextNode = None

Given this setup, an important demonstration is mutability, particularly when it comes to our custom class and passing an object as a parameter (and please note, this also applies to a list such as [1,2,3] as well).

def mutable_test(node):
    node.value = "Value was changed"

currentNode = Node("1")
print(currenNode.value)
mutable_test(currentNode)
print(currentNode.value)

Output:

1
Value was changed

This really highlights the importance of understanding how passing an object as a parameter to a function affects it. Even though I didn't return any value, or store it from a function call, my currentNode was still changed by mutabile_test. See below link for the related discussion that goes into a lot of detail on this.

Solution:

Given the explanation above, we can see where we might have some issues with your code, assuming otherwise it worked "as intended". With your function above, the intent does not seem to be to change the argument passed in, but rather create a list to return, which can be referenced and manipulated separate from the original Node.

We can use the following to do so:

def transformRecursive(node):
    # note the use of `is None` here
    if node is None:
        # return an empty list, see below reason
        return []
    else:
        # first we create the list in place
        result = [node.value]
        # we can then extend the result recursively, because if
        # we get an empty list, it simply won't be extended
        result.extend(transformRecursive(node.nextNode))
        # finally, return the extended result
        return result

Testing it out:

currentNode = Node("1")
currentNode.nextNode = Node("2")
currentNode.nextNode.nextNode = Node("3")

print(transformRecursive(currentNode))

Output:

['1', '2', '3']

Follow on topics for consideration:

You may want to see some related discussions:

Aelarion
  • 397
  • 4
  • 11