Loop infinito lettura dati da file

di il
10 risposte

Loop infinito lettura dati da file

Salve,
mi sto cimentando in un programma che prende degli interi da file, li memorizza in un array e li ordina mediante il metodo per fusione.
Sembrerà strano ma la cosa che più mi sta dando filo da torcere è la lettura da file.
Il mio obiettivo è quello di leggere degli interi in un file dove ci sono parole e numeri ma il problema è che i metodi
hasNext()
e
hasNextInt()
sembrano non funzionare e pertanto adesso sto provando semplicemente a leggere degli interi da file.
Posto un pezzo di codice per spiegare meglio la situazione:

Questo è il codice che si occupa di contare quanti numeri ci sono nel file

int numofint = 0; //questa variabile viene creata per poter salvare il numero di interi presenti nel file

while (in.hasNext())
{
	numofint++; //la variabile numofint viene incrementata
} //end of while
Questo ciclo while entra in un loop senza fine.... Non riesco comprendere il motivo...

Il resto del codice che si occupa di inserire gli interi nell'array è:

array = new int[numofint+1];

in.reset(); //reset dello scanner

int i=-1;
while (in.hasNext())
{
	i++;

	array[i] = Integer.parseInt(in.next());

} //end of while
Spero vivamente che qualcuno possa aiutarmi

Questo è il codice dell'intero programma (quello scritto fin ora):

package com_antomau_OrdFusRicBin.UserInterface;

import java.util.Scanner;
import javax.swing.*;
import java.awt.BorderLayout;
import java.awt.GridLayout;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
import java.io.*;
import java.util.Arrays;

/**
 * 
 * @author Antonio Maulucci
 *
 */
public class UserOrdFusRicBin {
	
	private static File file; //nuovo file
	
	private static Scanner in; //nuovo scanner
	
	/*
	 * fileLoaded -> verifica che il file sia stato correttaamente caricato
	 * arraySorted -> verifica che l'array sia stato ordinato
	 */
	private static boolean fileLoaded = false;
	private static int[] array;
	
	public static void main(String[] args) {
		
		
		JFrame f = new JFrame("OrdFus-RicBin");
		f.setSize(300, 300);
		f.setLayout(new BorderLayout());
		f.setVisible(true);
		f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		
		JPanel fileFinder = new JPanel();
		fileFinder.setLayout(new GridLayout(1,3));
		
		JFileChooser fileChooser = new JFileChooser();
		
		JLabel choosenFileName = new JLabel(""); 
		JButton openFileButton = new JButton("Open database");
		JButton exitButton = new JButton("Exit");
		
		fileFinder.add(choosenFileName);
		fileFinder.add(openFileButton);
		fileFinder.add(exitButton);
		
		
		JPanel contentPanel = new JPanel();
		contentPanel.setLayout(new BorderLayout());
		
		JPanel consolePanel = new JPanel();
		consolePanel.setLayout(new GridLayout(1,4));
		
		JButton printArrayButton = new JButton("Print data");
		JButton sortButton = new JButton("Sort");
		
		consolePanel.add(printArrayButton);
		consolePanel.add(sortButton);
		
		JPanel mainContents = new JPanel();
		
		contentPanel.add(consolePanel, BorderLayout.NORTH);
		contentPanel.add(mainContents, BorderLayout.CENTER);
		
		f.add(fileFinder, BorderLayout.NORTH);
		f.add(contentPanel, BorderLayout.CENTER);
		
		
		f.pack();
		
		class openFileListenerClass implements ActionListener {
			@Override
			public void actionPerformed(ActionEvent e) {
				fileChooser.showOpenDialog(f); //questa istruzione visualizza la finestra di dialogo per la scleta del file all'interno del frame f
				try {
					file = fileChooser.getSelectedFile();
					in = new Scanner(file); //creare uno scanner per il file "file"
					fileLoaded = true; //diventa vera perché il file è stato caricato
					
				} catch (FileNotFoundException ex) {
					ex.printStackTrace();
				} //end of try/catch
				//\\//\\//\\//\\//\\//
				if (fileLoaded)
				{

					int numofint = 0; //questa variabile viene creata per poter salvare il numero di interi presenti nel file

					while (in.hasNext())
					{
						numofint++; //la variabile values viene incrementata
					} //end of while

					array = new int[numofint+1];

					in.reset(); //reset dello scanner

					int i=-1;
					while (in.hasNext())
					{
						i++;

						array[i] = Integer.parseInt(in.next());

					} //end of while

				} //end of if fileLoaded
				//\\//\\//\\//\\//\\//
				choosenFileName.setText(fileChooser.getName(file));
			}
		} //end of selectFileListenerClass
		
		ActionListener openFileListener = new openFileListenerClass();
		openFileButton.addActionListener(openFileListener);
		
		
		class exitListenerClass implements ActionListener {
			@Override
			public void actionPerformed(ActionEvent e) {
				System.exit(0);
			}
		} //end of openFileListenerClass
		
		ActionListener exitListener = new exitListenerClass();
		exitButton.addActionListener(exitListener);
		
		class printDataButtonListenerClass implements ActionListener {
			@Override
			public void actionPerformed(ActionEvent e) {
				if (fileLoaded) {
					mainContents.removeAll();
					JLabel printArrayLabel = new JLabel(Arrays.toString(array));
					mainContents.add(printArrayLabel);
					f.pack();
				} //end of if
			}
		} //end of openFileListenerClass
		
		ActionListener printDataListener = new printDataButtonListenerClass();
		printArrayButton.addActionListener(printDataListener);
		
	} //end of main

} //end of class


Altri modi in cui ho provato ad implementare la lettura del numero di token e ad inserire questi nell'array sono stati:

metodo 1

if (fileLoaded) { //linea 93
   int[] k = new int[256];
   int i=-1;
   while (in.hasNext())
   {
      i++;
      k[i] = in.nextInt();
      System.out.print(i + " "); //debug
   } //end of while
   System.out.println("i = " + i); //debug
   array = new int[i+1];
   for (int j=0; j<i; j++) {
      array[i] = k[i];
   }
   System.out.println(Arrays.toString(array)); //debug
} //end of if
metodo 2

if (fileLoaded) { //linea 93
               //questa variabile salva il numero di elementi che dovrà contenere l'array di interi
               int values=0;
               while (in.hasNext()) values++;
               array = new int[values-1]; //l'array "array" viene inzializzato con n-1 posizioni dove n sono gli elementi da inserire (values) (n-1 perché le posizioni dell'array partono da 0, per 3 elementi servono 2 posizioni perché 0,1,2)
               int i = -1; //indice dell'array in cui inserire il dato corrente (vedi commento di "i++" per comprendere perché il suo valore è (-1)
               while (in.hasNext()) { // questo ciclo while verifica che nel file ci sia un dato successivo a quello seguente
                  if (in.hasNextInt()) {
                     /*
                      * l'indice dell'array viene incrementato per permettere di inserire il dato nel nuovo indice dell'array
                      * esso viene inzializzato a -1 per fare in modo che l'indice i sia incrementato prima dell'inserimento del nuovo dato
                      *  questo modo si fa prima corrispondere l'indice alla posizione corretta dell'elemento da inserire
                      *  e poi si inserisce l'elemento
                      *  altrimenti avverrebbe che all'ultimo intero il dato verebbe inserito e poi verrebbe incrementato l'indice verso una posizione inesistente il che genererebbe un errore
                      */
                     i++;
                     System.out.println("debug - i is = " + i + " /// in.nextint is = " + in.nextInt());
                     array[i] = in.nextInt(); //nella posizione i dell'array viene inserto il numero intero
                  } //end of if
               } //end of while
               //
            } //end of if
metodo 3

if (fileLoaded)
{
   in.reset(); //debug
   int values = 0;
   while (in.hasNextInt())
   {
      System.out.println("i'm incrementing values"); //debug
      values++;
      System.out.println("now values is = " + values); //debug
      if (in.hasNext()) System.out.println("next value is = " + in.next()); //debug
   } //end of while
   System.out.println("at end of while value of values is = " + values); //debug
   array = new int[values+1];
   int i = -1;
   try {
      in = new Scanner(file);
   } catch(Exception ex) {
      System.out.println("unable to make scanner"); //debug
   }
   /*
   while (in.hasNextInt()) //risulta essere falso
   {
      i++;
      System.out.println("after incrementing i it's = " + i); //debug
      array[i] = in.nextInt();
      System.out.println("ending while i is = " + i + " and nextInt is = " + in.nextInt()); //debug
   } //end of while
   */
   while(in.hasNextInt())
   {
      i++;
      System.out.println("after incrementing i it's = " + i); //debug
      array[i] = in.nextInt();
      System.out.println("ending while i is = " + i + " and nextInt is = " + in.nextInt()); //debug
   } //end of while
} //end of if fileloaded

10 Risposte

  • Re: Loop infinito lettura dati da file

    Altri modi in cui ho provato ad implementare la lettura del numero di token e ad inserire questi nell'array sono stati:

    metodo 1
    
    if (fileLoaded) { //linea 93
    	int[] k = new int[256];
    	int i=-1;
    	while (in.hasNext())
    	{
    		i++;
    		k[i] = in.nextInt();
    		System.out.print(i + " "); //debug
    	} //end of while
    	System.out.println("i = " + i); //debug
    	array = new int[i+1];
    	for (int j=0; j<i; j++) {
    		array[i] = k[i];
    	}
    	System.out.println(Arrays.toString(array)); //debug
    } //end of if
    
    metodo 2
    
    if (fileLoaded) { //linea 93
    					//questa variabile salva il numero di elementi che dovrà contenere l'array di interi
    					int values=0;
    					while (in.hasNext()) values++;
    					array = new int[values-1]; //l'array "array" viene inzializzato con n-1 posizioni dove n sono gli elementi da inserire (values) (n-1 perché le posizioni dell'array partono da 0, per 3 elementi servono 2 posizioni perché 0,1,2)
    					int i = -1; //indice dell'array in cui inserire il dato corrente (vedi commento di "i++" per comprendere perché il suo valore è (-1)
    					while (in.hasNext()) { // questo ciclo while verifica che nel file ci sia un dato successivo a quello seguente
    						if (in.hasNextInt()) {
    							/*
    							 * l'indice dell'array viene incrementato per permettere di inserire il dato nel nuovo indice dell'array
    							 * esso viene inzializzato a -1 per fare in modo che l'indice i sia incrementato prima dell'inserimento del nuovo dato
    							 *  questo modo si fa prima corrispondere l'indice alla posizione corretta dell'elemento da inserire
    							 *  e poi si inserisce l'elemento
    							 *  altrimenti avverrebbe che all'ultimo intero il dato verebbe inserito e poi verrebbe incrementato l'indice verso una posizione inesistente il che genererebbe un errore
    							 */
    							i++;
    							System.out.println("debug - i is = " + i + " /// in.nextint is = " + in.nextInt());
    							array[i] = in.nextInt(); //nella posizione i dell'array viene inserto il numero intero
    						} //end of if
    					} //end of while
    					//
    				} //end of if
    
    metodo 3
    
    if (fileLoaded)
    {
    	in.reset(); //debug
    	int values = 0;
    	while (in.hasNextInt())
    	{
    		System.out.println("i'm incrementing values"); //debug
    		values++;
    		System.out.println("now values is = " + values); //debug
    		if (in.hasNext()) System.out.println("next value is = " + in.next()); //debug
    	} //end of while
    	System.out.println("at end of while value of values is = " + values); //debug
    	array = new int[values+1];
    	int i = -1;
    	try {
    		in = new Scanner(file);
    	} catch(Exception ex) {
    		System.out.println("unable to make scanner"); //debug
    	}
    	/*
    	while (in.hasNextInt()) //risulta essere falso
    	{
    		i++;
    		System.out.println("after incrementing i it's = " + i); //debug
    		array[i] = in.nextInt();
    		System.out.println("ending while i is = " + i + " and nextInt is = " + in.nextInt()); //debug
    	} //end of while
    	*/
    	while(in.hasNextInt())
    	{
    		i++;
    		System.out.println("after incrementing i it's = " + i); //debug
    		array[i] = in.nextInt();
    		System.out.println("ending while i is = " + i + " and nextInt is = " + in.nextInt()); //debug
    	} //end of while
    } //end of if fileloaded
    
  • Re: Loop infinito lettura dati da file

    Più che gli svariati tentativi di codice, dovresti mostrare un esempio di file e cosa vuoi estrarre.
  • Re: Loop infinito lettura dati da file

    Chiedo venia...
    Il mio obiettivo sarebbe un programma che memorizzi in un array solamente i numeri interi contenuti nel file
    "data.dat"
    che contiene questo testo
    ciao 12 come 23 stai 34
    Ma mi accontento anche di un programma che legge gli interi da un file che contiene solo numeri interi come ad esempio
    numbers.dat
    1 3 25 69 102 125
  • Re: Loop infinito lettura dati da file

    antomau96 ha scritto:


    Il mio obiettivo sarebbe un programma che memorizzi in un array solamente i numeri interi contenuti nel file
    "data.dat"
    che contiene questo testo
    ciao 12 come 23 stai 34
    Semplicemente usi Scanner e in particolare hasNextInt(). Se hasNextInt() dà true, vuol dire che il prossimo token lo puoi leggere con nextInt(). Altrimenti se dà false usi next() per leggere (e "buttare via" se non ti serve per altro) il token che è qualunque altra cosa non int.

    Se il tuo dubbio è come realizzare un ciclo, la condizione del ciclo è semplicemente hasNext() ovvero se c'è un qualunque token. Poi cosa sia è appunto la logica detta poco fa.
  • Re: Loop infinito lettura dati da file

    Non so se hai letto il codice postato ma dubito... Di cicli while con quelle condizioni ne ho provati 5...
    Il problema è che dai cicli
    
    while (scanner.hasNext())
    {
    	counter++;
    }
    
    e
    
    while (scanner.hasNextInt())
    {
    	counter++;
    }
    
    non si esce mai e la variabile counter raggiunge valori enormi (testato mediante il debugger)
  • Re: Loop infinito lettura dati da file

    F27
    debugger


    contenuto del file

  • Re: Loop infinito lettura dati da file

    Ascolta: i metodi hasXXX NON "consumano" il token, non fanno avanzare lo Scanner. Ecco perché DEVI combinare in modo opportuno gli hasXXX con i nextXXX.

    Lo ripeto meglio: ciclo "finché c'è un qualunque token". Poi dentro: è un token int? Allora lo estrai come int. Non è un int? Lo estrai come token generico (e non lo usi, se non ti serve per altri motivi).

    Non so ... più di così ....
  • Re: Loop infinito lettura dati da file

    Ho definitivamente risolto il problema in questo modo
    
    if (fileLoaded)
    {
    	int values = 0; //questo valore memorizza il numero di interi presenti nel file
    	in.reset(); //reset dello scanner
    	while (in.hasNext())
    	{
    		if (isInteger(in.next())) values++;
    	} //end of whiile hasNext
    	int i=-1;
    	array = new int[values];
    	try {
    		in = new Scanner(file);
    	} catch (Exception exc) {
    		System.exit(10);
    	}
    	while (in.hasNext())
    	{
    		String input = in.next();
    		if (isInteger(input))
    		{
    			i++;
    			array[i] = Integer.parseInt(input);
    		} //end of if
    	} //end of while
    } //end of if fileloaded
    
    Ringrazio particolarmente @andbin per l'aiuto che mi ha fornito

    Adesso, avendo il file
    numbers.dat
    che contiene questi dati
    1 ciao 2 cane 3 gatto 4 pappagallo 5 pavone 16
    Il programma ha come output:


    Vi ringrazio ancora una volta per aver aiutato qualcuno a risolvere un problema

    Ovviamente il metodo isInteger non esiste e l'ho scritto io
    
    private static boolean isInteger(String str){
    	 try{
    		Integer.parseInt(str);
    		return true;
    	}catch(Exception e){
    		return false;
    	}
    }
    
  • Re: Loop infinito lettura dati da file

    Giusto per informazione, questo è quello che descrivevo prima io:
    Scanner sc = new Scanner("ciao 12 come 23 stai 34");
    
    while (sc.hasNext()) {
        if (sc.hasNextInt()) {
            System.out.println("int: " + sc.nextInt());
        } else {
            sc.next();   // butta via token non int (se non serve per altro)
        }
    }
    Che estrae e stampa solo gli interi. Tutto qui.
  • Re: Loop infinito lettura dati da file

    Grazie,
    in una delle varie implementazioni che avevo realizzato ho usato una struttura simile ma non mi era chiaro il concetto che i metodi hasXX non fanno scorrere lo scanner.
    Adesso ho sistemato il tutto seguendo questo "schema" che è molto più snello e funzionale.
Devi accedere o registrarti per scrivere nel forum
10 risposte