Springen naar inhoud

[java] arrayindexoutofboundsexception


  • Log in om te kunnen reageren

#1

floRobi

    floRobi


  • >25 berichten
  • 37 berichten
  • Gebruiker

Geplaatst op 26 maart 2008 - 10:31

Bij het maken van een oefening op arrays krijg ik ArrayIndexOutOfBoundsException-foutje.

De vraag: ( komt uit een VB.net leerboekje en ik probeer ze op te lossen in java )

Beschrijving
Maak een programma dat aan de gebruiker vraag hoeveel getallen er worden ingevoerd.

CreŽer een array die net voldoende elementen heeft om dit aantal getallen te stockeren.
Vul de array op met de door de gebruiker ingevoerde getallen.
Breng de inhoud van de array op de console.
Verwissel nu alle twee opeenvolgende getallen van positie. In onderstaand programa-verloop ( waar we 5 elementen in de array hebben ) worden de elementen op indexen 0 en 1 en op de indexen 2 en 3 met elkaar verwisseld. Indien de array een oneven aantal elementen heeft, hoeft het laatste getal niet van positie te veranderen.
Breng nu opnieuw de inhoud van de array op de console.
Zorg ervoor dat je programma exact hetzelfde programma-verloop heeft, met dezelfde output, als hieronder is weergegeven.

Programma-verloop ( invoer van de gebruiker ) :

Count : 5
Number 1 : 11
Number 2 : 22
Number 3 : 33
Number 4 : 44
Number 5 : 55
Numbers Before Shift : 11 22 33 44 55
Numbers After Shift : 22 11 44 33 55


en mijn code :

public class SwitchInputNumbers {
	 
		public static void main(String[] args) {
		
		
		/*int [] intArray;				  //declareer een array van integers
		intArray = new int[10];		   //hang er een feitelijke array achter, waarin 10 elementen zitten ( zowel maximaal als minimaal, de grens is vast)

		for(int i = 0; i < intArray.length; i ++)  //Loop de array door tot de maximale lengte, begin natuurlijk bij 0.
		{
		intArray[i] = i;			//Vul de array met nummers.
		System.out.print(intArray[i] + " ");
		}
 		System.out.println();*/
		
		  Input l = new Input();
		  System.out.print("Count : ");
		  int aantalNum = l.readInt();
		  int[] numbers;  // An array for storing the input values.
		  int numCt;	  // The number of numbers saved in the array.
		  int num;		// One of the numbers input by the user.
		  
		  numbers = new int[aantalNum];   // Space for x ints.
		  int[] list = new int[aantalNum];
		  numCt = 0;				// No numbers have been saved yet.
		  
					
		  while (true) {   // Get the numbers and put them in the array.
			 System.out.print("Number "+(numCt+1)+" : ");
			 num = l.readInt();
			 
			 numbers[numCt] = num;
			 list[numCt] = num;
			 numCt++;
			 
			 
			 if (numCt == aantalNum)
				break;
			 
		  } // end whilelus
		  
		  System.out.print("Numbers Before Shift : ");
		  
		  for (int i = 0; i <= numCt-1; i++) {
			  System.out.print( " " + numbers[i] + " " );
			  
		  } // end forlus
		  System.out.println("");
		  System.out.print("Numbers After Shift : ");
		  for (int i = -1; i <= numCt-1; i++) {
			  i=i+1;
			  int j=-1;
			  j=i+1;
			  
			  int a;
			  
			  a=i;
			  i=j;
			  j=a;
			  
			  
				System.out.print( " " + numbers[i] + " " );
			  System.out.print( " " + list[j] + " " );
			 i=a;
			 j=i;
			 
			  
		  } // end forlus
							 
				   
		  System.out.println("");
		} // end main();
		
	 }  // end class SwitchInputNumbers

Bij het laatste deel moet ik een keer j=i+1 en een keer i=i+1 om respectievelijk 0de,2de,4de,.. en 1ste,3de,5de,.. getallen te hebben uit mijn array, maar omdat ik i+1 doe ga ik volgens mij buiten mijn array.

Ik heb nog een array bijgemaakt met range [aantalNum+1] en als ik de array [aantalNum] naar [aantalNum+1] kopieer en het afbeeld op het scherm krijg ik nullen te zien.

Btw.. mijn werkwijze is hoogstwaarschijnlijk allesbehalve de juiste. :D

Bestaat er een syntax om 2 getallen van een array van plaats te wisselen? Iemand suggestie?

Dit forum kan gratis blijven vanwege banners als deze. Door te registeren zal de onderstaande banner overigens verdwijnen.

#2

EvilBro

    EvilBro


  • >5k berichten
  • 6703 berichten
  • VIP

Geplaatst op 26 maart 2008 - 11:07

Btw.. mijn werkwijze is hoogstwaarschijnlijk allesbehalve de juiste. :D


Het probleem is dat je werkwijze slordig is, waardoor je het overzicht verliest en het jezelf moeilijker maakt dan het daadwerkelijk is. Dit leidt tot het soort fouten die je nu tegenkomt.

while (true) {   // Get the numbers and put them in the array.
Je weet al hoeveel nummers je gaat krijgen. Gebruik dus een for-lus.
for (int i = 0; i < aantalNum; i++) {
  System.out.print("Number "+(numCt+1)+" : ");
  num = l.readInt();
  numbers[i] = num;
}

Het volgende:
for (int i = 0; i <= numCt-1; i++)
is equivalent met:
for (int i = 0; i < aantalNum; i++)
Dit laatste geeft weer wat je wil doen (in tegenstelling tot het eerste wat 'toevallig' hetzelfde doet).

for (int i = -1; i <= numCt-1; i++) {
			  i=i+1;
			  int j=-1;
			  j=i+1;
Wederom vaag. Vermoedelijk verzin je wat je wilt doen terwijl je aan het tikken bent. Dit is niet handig. Stapje terug doen. Even afstand bewaren en je ziet:
for (int i = 0; i < aantalNum; i++) {
  int j= i+1;
Dan zie je ook dat even later de volgende code helemaal niks zinnigs doet:
i=a;
j=i;
Zie je waarom? (Edit: ik geloof dat ik me hier vergist heb. De code is noodzakelijk omdat je de zonde begaat dat je je loop-variabele aanpast. Dat is een erg slecht idee, want dat leidt tot onoverzichtelijke code.)

De tip die ik geef is dus dat je het geheel abstracter aanpakt. Probeer deeltaken te zien. Je begint dus met:
* lees hoeveel getallen er gelezen moeten worden.
* lees zoveel getallen.
* print deze getallen.
* verwissel de paartjes getallen van positie.
* print de nieuwe volgorde.
Eventueel kun je deze deeltaken nog verder opsplitsen. Ook is het gebruik van methodes aan te raden (deeltaak = een methode). Hierdoor bewaar je ook beter overzicht over wat je wilt bereiken met een stukje code.

#3

Cycloon

    Cycloon


  • >1k berichten
  • 4810 berichten
  • VIP

Geplaatst op 26 maart 2008 - 19:06

Ik heb nog een array bijgemaakt met range [aantalNum+1] en als ik de array [aantalNum] naar [aantalNum+1] kopieer en het afbeeld op het scherm krijg ik nullen te zien.


Wat versta je onder kopiŽren? Alle waardes 1 voor 1 kopiŽren? Enkel gelijk stellen aan mekaar (referenties dus uitwisselen)? Of hoe doe je dit precies?

#4

EvilBro

    EvilBro


  • >5k berichten
  • 6703 berichten
  • VIP

Geplaatst op 26 maart 2008 - 20:48

Ik heb je code wat opgeschoond. Ik heb deze code niet getest, dus er zouden best wat fouten in kunnen zitten. Hopelijk verduidelijkt deze code dat een systematische aanpak een duidelijker programma oplevert.

public class SwitchInputNumbers {
  public static void main(String[] args) {

	Input l = new Input();
	System.out.print("Count : ");
	int aantalNum = l.readInt();

	int[] numbers = new int[aantalNum];  // An array for storing the input values.
	for (int numCt = 0; numCt < aantalNum; numCt++) {
			 System.out.print("Number " + (numCt+1) +" : ");
			 numbers[numCt] = l.readInt();
	}

	System.out.print("Numbers Before Shift : ");
	printNumbers(numbers);
  
	numbers = swapNumbers(numbers);

	System.out.print("Numbers After Shift : ");
	printNumbers(numbers);
  } // end main();

  // prints all numbers in the array with a space between them, ending with a newline.
  public static void printNumbers(int[] nums) {
	for (int i = 0; i < nums.length; i++) {
	  System.out.print( " " + nums[i] + " " );
	}
	System.out.println("");
  }

  // swap the value at the uneven position in the array with the value preceding it.
  public static int[] swapNumbers(int[] nums) {
	for (int i = 1; i < nums.length; i = i + 2) {
		int temp = nums[i-1];
		nums[i-1] = nums[i];
		nums[i] = temp;
	}
	return nums;
  }
}  // end class SwitchInputNumbers

#5

*_gast_PeterPan_*

  • Gast

Geplaatst op 26 maart 2008 - 22:50

Merk ook de plaats waar Evilbro zijn commentaren plaatst.
Je code ziet er mede rommelig uit vanwege de plaats en overbodigheid van veel commentaren.

V.b. intArray[i] = i; //Vul de array met nummers.
Dat zie ik ook wel. Ik zie zelfs met welke getallen.

Het enige wat ik in Evilbro's code minder geslaagd vind is de letter I (of staat er l, in ieder geval is het teken gelijk aan het teken voor 1) in
Input l = new Input();

#6

floRobi

    floRobi


  • >25 berichten
  • 37 berichten
  • Gebruiker

Geplaatst op 27 maart 2008 - 00:21

Ik begin het stillekes aan te snappen. Bedankt heren!

Wat versta je onder kopiŽren? Alle waardes 1 voor 1 kopiŽren? Enkel gelijk stellen aan mekaar (referenties dus uitwisselen)? Of hoe doe je dit precies?

Ja, ik had het enkel gelijk gesteld aan mekaar, 'klein'-foutje. :/

Het enige wat ik in Evilbro's code minder geslaagd vind is de letter I (of staat er l, in ieder geval is het teken gelijk aan het teken voor 1) in
Input l = new Input();

Mijn fout. Er staat inderdaad een l. Ik had beter 'keyboard' moeten gebruiken..

EvilBro, ik heb je code doorgenomen en ik snap het volledig. Nogmaals bedankt.

Ik heb nog veel werk voor de boeg ťh?

Veranderd door floRobi, 27 maart 2008 - 00:27


#7

zpidermen

    zpidermen


  • >1k berichten
  • 1623 berichten
  • Ervaren gebruiker

Geplaatst op 27 maart 2008 - 07:40

Mijn fout. Er staat inderdaad een l. Ik had beter 'keyboard' moeten gebruiken..

Nee, da's ook geen goede naam. Waarom gebruik je niet gewoon:
Input input = new Input();
Beter kaal als geen haar want een kip snurkt

#8

Ruben01

    Ruben01


  • >1k berichten
  • 2902 berichten
  • Ervaren gebruiker

Geplaatst op 27 maart 2008 - 09:33

Nee, da's ook geen goede naam. Waarom gebruik je niet gewoon:

Input input = new Input();

Ik begrijp niet waarom l geen goede naam is ?
Het is misschien een klein beetje onduidelijk het verschil tussen de l en de i maar wanneer je iets zelf schrijft dan weet je toch duidelijk wat je gebruikt !
Ik gebruik persoonlijk ook altijd l omdat men dat zo heeft aangeleerd, in mijn cursus gebruiken ze altijd Input inp = ...
maar waarom meerdere letters typen als je veel sneller kan werken door het gebruik van 1 letter.
BOINC mee met het WSF-team: <a href="http://www.wetenscha...howtopic=60653" target="_blank">http://www.wetenscha...topic=60653</a>

#9

EvilBro

    EvilBro


  • >5k berichten
  • 6703 berichten
  • VIP

Geplaatst op 27 maart 2008 - 10:12

Het is misschien een klein beetje onduidelijk het verschil tussen de l en de i maar wanneer je iets zelf schrijft dan weet je toch duidelijk wat je gebruikt !

Nu denk je misschien dat het duidelijk is wat je schrijft, maar als je je code over een paar maanden terug ziet dan weet je het niet meer.

Ik gebruik persoonlijk ook altijd l omdat men dat zo heeft aangeleerd, in mijn cursus gebruiken ze altijd Input inp = ...

Dit laatste is veel beter.

maar waarom meerdere letters typen als je veel sneller kan werken door het gebruik van 1 letter.

Dit is een vorm van kortzichtigheid. Het 'extra' werk dat je nu creeert (de twee extra letters) besparen je veel meer werk in de toekomst.

Daar komt nog bij dat het nu gaat om een klein programma. Op het moment dat je echte programma's gaat schrijven, kom je er wel achter dat je methode voor naamgeving niet prettig werkt. Maar ja, dan is het al te laat, want je hebt het jezelf immers zo aangeleerd...

#10

Ruben01

    Ruben01


  • >1k berichten
  • 2902 berichten
  • Ervaren gebruiker

Geplaatst op 27 maart 2008 - 10:21

Ik kan begrijpen dat wanneer je werkt in grotere programma's dat het inderdaad voor problemen kan beginnen zorgen.
Jij weet hierover veel meer als mij dus ga ik bij mijn volgende programma overschakelen denk ik naar Input inp = new Input().
Input keyboard = new Input() dat is er nu net iets over dus zal ikzelf nooit gebruiken.
BOINC mee met het WSF-team: <a href="http://www.wetenscha...howtopic=60653" target="_blank">http://www.wetenscha...topic=60653</a>

#11

EvilBro

    EvilBro


  • >5k berichten
  • 6703 berichten
  • VIP

Geplaatst op 27 maart 2008 - 10:33

Ik kan begrijpen dat wanneer je werkt in grotere programma's dat het inderdaad voor problemen kan beginnen zorgen.

Het wordt helemaal leuk als anderen met je code verder moeten gaan. :D

#12

floRobi

    floRobi


  • >25 berichten
  • 37 berichten
  • Gebruiker

Geplaatst op 27 maart 2008 - 11:01

Input input = new Input();

Dit zou ik zelf nooit gebruiken, ik vind het verwarrend.

Input l = new Input();
Input inp = new Input();

Die twee gebruik(t)en we ook op school.

Input keyboard = new Input();

Nu en dan gebruik ik deze, omdat het direct naar het input verwijst. Duidelijker, maar ik weet niet of in java functies ofzo zijn die met 'keyboard' beginnen.
Magoed, ik zal voortaan inp gebruiken :P

Klein extraatje toegevoegd. 'reverse' numbers :D

public class SwitchInputNumbers {
  public static void main(String[] args) {

	Input inp = new Input();
	System.out.print("Count : ");
	int aantalNum = inp.readInt();
	int[] numbers = new int[aantalNum];  // An array for storing the input values.
	for (int numCt = 0; numCt < aantalNum; numCt++) {
			 System.out.print("Number " + (numCt+1) +" : ");
			 numbers[numCt] = inp.readInt();
			 
	}
	
	System.out.print("Numbers In Reverse Order : ");
	reverseNumbers(numbers);
	
	System.out.print("Numbers Before Shift : ");
	printNumbers(numbers);
  
	numbers = swapNumbers(numbers);

	System.out.print("Numbers After Shift : ");
	printNumbers(numbers);
  } // end main();


  // prints all numbers in the array in reverse order with a space between them, ending with a newline.
  public static void reverseNumbers(int[] nums) {
	for (int i = nums.length-1; i >= 0; i--) {
	  System.out.print( " " + nums[i] + " " );
	}
	System.out.println("");
  }

  // prints all numbers in the array with a space between them, ending with a newline.
  public static void printNumbers(int[] nums) {
	for (int i = 0; i < nums.length; i++) {
	  System.out.print( " " + nums[i] + " " );
	}
	System.out.println("");
  }

  // swap the value at the uneven position in the array with the value preceding it.
  public static int[]  swapNumbers(int[] nums) {
	for (int i = 1; i < nums.length; i = i + 2) {
		int temp = nums[i-1];
		nums[i-1] = nums[i];
		nums[i] = temp;
	}
	return nums;
  }
}  // end class SwitchInputNumbers

Ik vroeg me ook af waarom er static bij die methodes moest staan. Ik heb ze verwijderd, gecompiled en ik zag dat je niets van methoden kunt terugroepen via je main. Ooit las ik ergens van klasse- en instantie variabele maar ik weet het niet meer. Is dit de reden?

#13

EvilBro

    EvilBro


  • >5k berichten
  • 6703 berichten
  • VIP

Geplaatst op 27 maart 2008 - 11:21

Ik vroeg me ook af waarom er static bij die methodes moest staan.

Methodes horen normaal gesproken bij een object. Als dat object er niet is dan zijn die methodes er ook niet. Op het moment dat je een methode static maakt dan bestaat de methode los van alle mogelijke objecten van die klasse.

In het programma dat je runt maak je helemaal geen object. Als de methodes niet static zouden zijn, zouden ze dan dus niet bestaan. Ze zijn dan ook niet aan te roepen. Doordat de methodes static zijn bestaan ze los van eventuele objecten. Daardoor zijn ze wel aan te roepen (want ze bestaan).

#14

Cycloon

    Cycloon


  • >1k berichten
  • 4810 berichten
  • VIP

Geplaatst op 27 maart 2008 - 11:25

Die static staat er zodanig dat je geen object moet aanmaken van je klasse. Als je die static weghaalt moet je dat uiteraard wel doen en dan krijg je dit als main:

public static void main(String[] args) {

	Input inp = new Input();
	SwitchInputNumbers sin = new SwitchInputNumbers();
	System.out.print("Count : ");
	int aantalNum = inp.readInt();
	int[] numbers = new int[aantalNum];  // An array for storing the input values.
	for (int numCt = 0; numCt < aantalNum; numCt++) {
			 System.out.print("Number " + (numCt+1) +" : ");
			 numbers[numCt] = inp.readInt();
			
	}
	
	System.out.print("Numbers In Reverse Order : ");
	sin.reverseNumbers(numbers);
	
	System.out.print("Numbers Before Shift : ");
	sin.printNumbers(numbers);
  
	numbers = sin.swapNumbers(numbers);

	System.out.print("Numbers After Shift : ");
	sin.printNumbers(numbers);
  } // end main();

#15

floRobi

    floRobi


  • >25 berichten
  • 37 berichten
  • Gebruiker

Geplaatst op 27 maart 2008 - 11:36

Ik begrijp het. Bedankt voor de uitleg, heren.





0 gebruiker(s) lezen dit onderwerp

0 leden, 0 bezoekers, 0 anonieme gebruikers

Ook adverteren op onze website? Lees hier meer!

Gesponsorde vacatures

Vacatures