Lista jednokierunkowa w C - wpisywanie i wypisywanie

0

Witam.
Mam zapewne banalny problem, jednak sam siedzę nad tym już kilka godzin i nie mam pojęcia gdzie jest błąd.
Otóż, uzupełniając listę jednokierunkową, a później ją wypisując na ekranie jako pierwszy element wypisywany jest adres komórki a nie jej zawartość.
Podejrzewam, że problem jest gdzieś przy przypisywaniu pierwszego elementu, jednak na różne sposoby próbowałem modyfikować kod, lecz on wciąż nie działa.
Ten prostu program ma pobierać liczby od użytkownika aż do momentu podania liczby 0 i wpisywać ją na listę jednokierunkową, a następnie ma za zadanie wypisać tą listę.

#include <stdio.h>
#include <stdlib.h>

struct element {
    int liczba;
    struct element* next;
};
typedef struct element ELEMENT;
typedef ELEMENT* ADRES;

void utworzliste(ADRES lista)
{
    int i, licz;
    for (i = 0;; i++) {
        ADRES tmp = (ADRES)malloc(sizeof(ELEMENT));
        printf("Podaj %d liczbe calkowita: ", i + 1);
        scanf("%d", &licz);
        if (licz == 0)
            break;
        tmp->liczba = licz;
        tmp->next = NULL;
        if (lista == NULL)
            lista = tmp;
        else {
            lista->next = tmp;
            lista = lista->next;
        }
    }
}
void wyswietl(ADRES lista)
{
    int i;
    for (i = 0;; i++) {
        printf("%d . liczba wynosi %d \n", i + 1, lista->liczba);
        if (lista->next == NULL)
            break;
        lista = lista->next;
    }
}
int main()

{

    ADRES lista1 = (ADRES)malloc(sizeof(ELEMENT));

    utworzliste(lista1);

    wyswietl(lista1);

    return 0;
}
1

To nie jest adres, tylko losowa wartość z pamięci, bo nigdzie nie przypisujesz wartości pierwszemu elementowi listy.

0

Faktycznie, masz rację.
A jakim warunkiem wykryć pierwszy element? Bo rozumiem że mój warunek

if(lista==NULL)
lista=tmp;

nie będzie nigdy wykonany.
W jaki sposób można zrobić by przy pierwszej iteracji zostało wykonane przypisanie do pierwszego elementu?

1

Najłatwiej chyba po prostu traktować pierwszy element jako "głowę" bez żadnej wartości i wyświetlać od następnego.

0

Piękno w prostocie! Bardzo dziękuję za pomoc.

1

W main() zamiast

ADRES lista1 = (ADRES)malloc(sizeof(ELEMENT));

dać

ADRES lista1 = NULL;

Dodatkowo, przed wyświetleniem, sprawdzić czy lista nie jest pusta.
Edit:
Aby zmiany w funkcji w takim wypadku przyniosły efekt musisz przekazać wskaźnik przez referencję lub zwrócić jego zmienioną wartość.

0

No własnie próbowałem zrobić

ADRES lista1 = NULL;

ale wtedy program się nawet nie kompilował.
A w jaki sposób przekazać wskaźnik przez referencję?
Próbowałem:

utworzliste(*lista1);

ale to pewnie nie o to chodzi, bo też wtedy nie działa.

0

Piszesz w C, więc nie masz referencji (a jak piszesz w C++ to nie wymyślaj własnej listy, tylko użyj std::list albo std::forward_list - o ile w ogóle musisz użyć listy zamiast bardziej sensownego std::vector). Możesz przekazać wskaźnik na wskaźnik.

0

Zwrócenie wartości:

  1. deklaracja
    ADRES utworzliste(ADRES lista)
  2. dopisanie na końcu return lista;
  3. wywołanie
    lista1 = utworzliste(lista1);

Przekazanie wskaźnika przez wskaźnik:

  1. deklaracja
    void utworzliste(ADRES *lista)
  2. w funkcji zamiana wszystkich lista na (*lista)
  3. wywołanie
    utworzliste(&lista1);

1 użytkowników online, w tym zalogowanych: 0, gości: 1, botów: 0