Python function error ("is not defined")

0

This was the simplest code I found in a python-chained list, I just could not figure out why it's not working

class NodoLista:
    #Esta classe representa um nodo de uma lista encadeada.
    def __init__(self, dado=0, proximo_nodo=None):
        self.dado = dado
        self.proximo = proximo_nodo

    def __repr__(self):
        return '%s -> %s' % (self.dado, self.proximo)

class ListaEncadeada:
    #Esta classe representa uma lista encadeada.
    def __init__(self):
        self.cabeca = None

    def __repr__(self):
        return("[" + str(self.cabeca) + "]")

    print('Teste')

    def insere_no_inicio(lista, novo_dado):
        # 1) Cria um novo nodo com o dado a ser armazenado.
        novo_nodo = NodoLista(novo_dado)

        # 2) Faz com que o novo nodo seja a cabeça da lista.
        novo_nodo.proximo = lista.cabeca

        # 3) Faz com que a cabeça da lista referencie o novo nodo.
        lista.cabeca = novo_nodo

    def insere_depois(lista, nodo_anterior, novo_dado):
        assert nodo_anterior, "Nodo anterior precisa existir na lista."

        # Cria um novo nodo com o dado desejado.
        novo_nodo = NodoLista(novo_dado)

        # Faz o próximo do novo nodo ser o próximo do nodo anterior.
        novo_nodo.proximo = nodo_anterior.proximo

        # Faz com que o novo nodo seja o próximo do nodo anterior.
        nodo_anterior.proximo = novo_nodo


lista = ListaEncadeada()
print('Lista vazia:', lista)

insere_no_inicio(lista, 5)
print("Lista contém um único elemento:", lista)

nodo_anterior = lista.cabeca
insere_depois(lista, nodo_anterior, 10)
print("Inserindo um novo elemento depois de um outro:", lista)
    
asked by anonymous 29.11.2018 / 04:02

1 answer

1

Hello,

It does not work because of a simple indentation problem.

As the code is structured, the insere_no_inicio and insere_depois functions are defined within the scope of the ListaEncadeada class. Thus, only one instance of this class could call these functions.

The correct one would be:

class NodoLista:
    #Esta classe representa um nodo de uma lista encadeada.
    def __init__(self, dado=0, proximo_nodo=None):
        self.dado = dado
        self.proximo = proximo_nodo

    def __repr__(self):
        return '%s -> %s' % (self.dado, self.proximo)

class ListaEncadeada:
    #Esta classe representa uma lista encadeada.
    def __init__(self):
        self.cabeca = None

    def __repr__(self):
        return("[" + str(self.cabeca) + "]")

print('Teste')

def insere_no_inicio(lista, novo_dado):
    # 1) Cria um novo nodo com o dado a ser armazenado.
    novo_nodo = NodoLista(novo_dado)

    # 2) Faz com que o novo nodo seja a cabeça da lista.
    novo_nodo.proximo = lista.cabeca

    # 3) Faz com que a cabeça da lista referencie o novo nodo.
    lista.cabeca = novo_nodo

def insere_depois(lista, nodo_anterior, novo_dado):
    assert nodo_anterior, "Nodo anterior precisa existir na lista."

    # Cria um novo nodo com o dado desejado.
    novo_nodo = NodoLista(novo_dado)

    # Faz o próximo do novo nodo ser o próximo do nodo anterior.
    novo_nodo.proximo = nodo_anterior.proximo

    # Faz com que o novo nodo seja o próximo do nodo anterior.
    nodo_anterior.proximo = novo_nodo


lista = ListaEncadeada()
print('Lista vazia:', lista)

insere_no_inicio(lista, 5)
print("Lista contém um único elemento:", lista)

nodo_anterior = lista.cabeca
insere_depois(lista, nodo_anterior, 10)
print("Inserindo um novo elemento depois de um outro:", lista)

Output

Teste
Lista vazia: [None]
Lista contém um único elemento: [5 -> None]
Inserindo um novo elemento depois de um outro: [5 -> 10 -> None]

Another option

Another possibility would be to actually do functions insere_no_inicio and insere_depois methods of class ListaEncadeada . This way:

class NodoLista:
    #Esta classe representa um nodo de uma lista encadeada.
    def __init__(self, dado=0, proximo_nodo=None):
        self.dado = dado
        self.proximo = proximo_nodo

    def __repr__(self):
        return '%s -> %s' % (self.dado, self.proximo)

class ListaEncadeada:
    #Esta classe representa uma lista encadeada.
    def __init__(self):
        self.cabeca = None

    def __repr__(self):
        return("[" + str(self.cabeca) + "]")

    def insere_no_inicio(self, novo_dado):
        # 1) Cria um novo nodo com o dado a ser armazenado.
        novo_nodo = NodoLista(novo_dado)

        # 2) Faz com que o novo nodo seja a cabeça da lista.
        novo_nodo.proximo = self.cabeca

        # 3) Faz com que a cabeça da lista referencie o novo nodo.
        self.cabeca = novo_nodo

    def insere_depois(self, nodo_anterior, novo_dado):
        assert nodo_anterior, "Nodo anterior precisa existir na lista."

        # Cria um novo nodo com o dado desejado.
        novo_nodo = NodoLista(novo_dado)

        # Faz o próximo do novo nodo ser o próximo do nodo anterior.
        novo_nodo.proximo = nodo_anterior.proximo

        # Faz com que o novo nodo seja o próximo do nodo anterior.
        nodo_anterior.proximo = novo_nodo

print('Teste')

lista = ListaEncadeada()
print('Lista vazia:', lista)

lista.insere_no_inicio(5)
print("Lista contém um único elemento:", lista)

nodo_anterior = lista.cabeca
lista.insere_depois( nodo_anterior, 10)
print("Inserindo um novo elemento depois de um outro:", lista)

Output

Teste
Lista vazia: [None]
Lista contém um único elemento: [5 -> None]
Inserindo um novo elemento depois de um outro: [5 -> 10 -> None]
    
29.11.2018 / 04:26