#java #list #object #linked-list #model
Вопрос:
Я пытаюсь реализовать связанный список в java, консультируясь с учебником моей школы.
Чтобы просмотреть список, я использую метод getInfo()
для каждого узла, который должен возвращать имя и фамилию каждого человека в списке (я создаю список людей).
Я не понимаю, почему мой учебник в методе getInfo()
узла класса возвращает a new Invitato(info)
, а не тот, который хранится в классе Nodo
.
Если я попытаюсь вернуть того , кто хранится в классе Nodo
, я получу исключение с нулевым указателем.
public class Main{
public static void main(String args[]){
Invitato i1 = new Invitato("Michele","Bianchi");
Invitato i2 = new Invitato("Paolo","Rossi");
Invitato i3 = new Invitato("Mario","Verdi");
Invitato i4 = new Invitato("Giacomo","Neri");
Lista l = new Lista();
l.inserisciInCoda(i1);
l.inserisciInTesta(i2);
l.inserisciInTesta(i3);
l.inserisciInPosizione(i4,2);
l.visitaLista();
}
}
public class Lista{
private Nodo head;
private int elementi;
public Lista(){
elementi=0;
head = null;
}
private Nodo creaNodo(Invitato invitato, Nodo link){
Nodo nuovoNodo = new Nodo(invitato);
nuovoNodo.setLink(link);
return nuovoNodo;
}
public int getElementi(){
return elementi;
}
private Nodo getLinkPosizione(int n){
Nodo p = head;
int i = 1;
if(n>elementi || n<1)
return null;
else{
while(p.getLink() != null amp;amp; i<n){
p = p.getLink();
i ;
}
}
return p;
}
public void visitaLista(){
Nodo p = head;
if(p==null){
System.out.println("Lista vuota");
}
else{
while(p!=null){
System.out.println(p.getInfo().toString());
p = p.getLink();
}
}
}
public void inserisciInTesta(Invitato invitato){
Nodo p = creaNodo(invitato, head); //creo un nuovo nodo e lo liko alla testa
head = p; //il nuovo nodo diventa la head
elementi ;
}
public void inserisciInCoda(Invitato invitato){
if(head==null){ //se la lista è vuota
inserisciInTesta(invitato); //posso inserire il nuovo nodo in testa
}
else{
Nodo p = getLinkPosizione(elementi); //prendo l'ultimo nodo
Nodo nuovoNodo = creaNodo(invitato, null);
p.setLink(nuovoNodo);
elementi ;
}
}
public void inserisciInPosizione(Invitato invitato, int posizione){
if(posizione <=1){
inserisciInTesta(invitato);
}
else{
if(posizione > elementi){
inserisciInCoda(invitato);
}
else{
Nodo p = getLinkPosizione(posizione-1);
Nodo nuovoNodo = creaNodo(invitato,p.getLink());
p.setLink(nuovoNodo);
elementi ;
}
}
}
public void eliminaInTesta(){
if(head == null) //la lista è vuota?
return;
head = head.getLink(); //la nuova head è il nodo a cui linka, quindi ora head riferisce al secondo nodo
elementi--;
}
public void eliminaInCoda(){
if(head == null){ //lista vuota
return;
}
Nodo p = getLinkPosizione(elementi-1); //prendo il penultimo nodo
p.setLink(null); // e metto il suo link a null
elementi--;
}
public void eliminaInPosizione(int n){
if(n<=1){
this.eliminaInTesta();
}
else{
if(n>=elementi){
this.eliminaInCoda();
}
else{
Nodo pp = getLinkPosizione(n-1); //nodo prima di quello da cancellare
Nodo ps = getLinkPosizione(n); //nodo da cancellare
pp.setLink(ps.getLink()); //assegno al link precedente a quello da cancellare il link di quello che sto cancellando
elementi--;
}
}
}
}
public class Invitato{
private String nome;
private String cognome;
public Invitato(String nome, String cognome){
this.nome = nome;
this.cognome = cognome;
}
public Invitato(Invitato invitato){
this.nome = invitato.getNome();
this.cognome = invitato.getCognome();
}
public String getNome(){
return nome;
}
public String getCognome(){
return cognome;
}
public String toString(){
return nome " " cognome ";";
}
}
public class Nodo{
private Invitato info;
private Nodo link;
public Nodo(Invitato invitato){
this.invitato = new Invitato(invitato);
link = null;
}
public Invitato getInfo(){
return new Invitato(info);
}
public void setLink(Nodo link){
this.link = link;
}
public Nodo getLink(){
return link;
}
}
Комментарии:
1. getInfo() возвращает копию приглашения в Nodo. Не видя полной трассировки стека вашего NPE, невозможно определить, что не так.
2. Небольшой совет на будущее: пишите код на английском, а не на итальянском. Конечно, код все равно будет работать, но кому-то становится трудно читать и понимать, что вы делаете (даже мне, а я итальянец!)
3. Это вообще компилируется? В
Nodo
конструкторе вашего класса у вас естьthis.invitato = ...
, но у этого класса нет никакого поля с именемinvitato
.
Ответ №1:
Конструктор Nodo неверен:
this.invitato = new Invitato(invitato);
должно быть:
this.info= new Invitato(invitato);
И вам не нужно создавать новый экземпляр Invitato в конструкторе Nodo и в getInfo
методе:
public Nodo(Invitato invitato){
this.info = invitato;
link = null;
}
public Invitato getInfo(){
return info;
}
Как только конструктор исправлен, у меня есть список без каких-либо исключений:
Mario Verdi;
Giacomo Neri;
Paolo Rossi;
Michele Bianchi;
Комментарии:
1. Большое спасибо, за исключением несоответствия информации и приглашения, я использовал свой подход из учебника, который для меня не имел смысла.