1. Nimm jetzt an unserem Uhans - 3. ADVENT - Gewinnspiel teil - Alle Informationen findest Du hier!

ArrayIndexOutOfBoundsException

Dieses Thema im Forum "Android App Entwicklung" wurde erstellt von Mort, 08.10.2010.

  1. Mort, 08.10.2010 #1
    Mort

    Mort Threadstarter Android-Lexikon

    Beiträge:
    960
    Erhaltene Danke:
    262
    Registriert seit:
    16.11.2009
    Hallo, mal ein Problem, dass wahrscheinlich nicht mit Android zu tun hat, mich aber schon länger nervt.
    Ich habe für die "mischen über alle Ordner"-Funktion im MortPlayer folgenden Code (leicht gekürzt):
    Code:
    Random rand = new Random( new Date().getTime() );
    int start = 0;
    List<Integer> foldersDeck = new ArrayList<Integer>();
    List<Integer> filesDeck = new ArrayList<Integer>();
            
    for ( alle Dateien in den ersten, zufälligen Ordnern ) {
        foldersDeck.add( shuffleFolders[i] );
        filesDeck.add( ii );
    }
            
    int fileCount = Math.min(maxFilesForShuffleAll, filesDeck.size());
    shuffleFolders = new int[fileCount];
    shuffleFiles   = new int[fileCount];
    
    /* etwas Handling um aktuelle und ggf. gewählte nächste Datei an den
    Anfang der Liste zu setzen */
    
    for ( int i = start; i < fileCount && filesDeck.size() > 0; i++ ) {
        pos = rand.nextInt( filesDeck.size() );
        shuffleFolders[i] = foldersDeck.get(pos);
        shuffleFiles[i]   = filesDeck.get(pos);
        foldersDeck.remove(pos);
        filesDeck.remove(pos);
    }
    (shuffleFolders und shuffleFiles sind private int[]-Properties der Klasse)

    Jetzt bekomme ich gelegentlich Fehlermeldungen, die eine ArrayIndexOutOfBoundsException bei "shuffleFolders = foldersDeck.get(pos);" enthalten. Ich kann mir aber nicht erklären, wie das zustande kommen kann, und selbst konnte ich den Fehler noch nicht nachvollziehen. Übersehe ich irgendwas wichtiges?
    Eigentlich müssten foldersDeck und filesDeck gleich groß sein, sie werden an nur einer Stelle gleichzeitig gefüllt. rand.nextInt dürfte keinen Wert über dem höchsten Index liefern. i kann nicht größer als fileCount werden, das kurz vorher als Array-Größe verwendet wurde. Wo kommt da ein ungültiger Index her???
    (Dass shuffeFiles/Folders zwischendurch per Multithreading auf andere Arrays zeigen ist übrigens auch sehr unwahrscheinlich, der Code läuft in einem synchronized-Block und wird ohnehin nicht allzu oft aufgerufen).
     
  2. swordi, 08.10.2010 #2
    swordi

    swordi Gewerbliches Mitglied

    Beiträge:
    3,389
    Erhaltene Danke:
    441
    Registriert seit:
    09.05.2009
    was sein könnte

    pos = rand.nextInt( filesDeck.size() );

    pos kann hier gleich der size sein

    beim get müsste es aber dann pos-1 sein, da 0 basiert

    beispiel

    filesDeck hat 10 einträge

    pos = 10 ( weil .size() )

    get(10) ist aber zuviel, da 0-9

    lg
     
  3. Mort, 08.10.2010 #3
    Mort

    Mort Threadstarter Android-Lexikon

    Beiträge:
    960
    Erhaltene Danke:
    262
    Registriert seit:
    16.11.2009
    Laut JavaDoc eigentlich nicht: "Returns a pseudorandom, uniformly distributed int value between 0 (inclusive) and the specified value (exclusive), drawn from this random number generator's sequence."
     
  4. swordi, 08.10.2010 #4
    swordi

    swordi Gewerbliches Mitglied

    Beiträge:
    3,389
    Erhaltene Danke:
    441
    Registriert seit:
    09.05.2009
    ok

    aber war ein versuch wert ;)
     
  5. ko5tik, 08.10.2010 #5
    ko5tik

    ko5tik Android-Experte

    Beiträge:
    620
    Erhaltene Danke:
    40
    Registriert seit:
    14.10.2009
    Phone:
    HTC Hero
    Poste mal deine Stacktrace....
     
  6. Mort, 08.10.2010 #6
    Mort

    Mort Threadstarter Android-Lexikon

    Beiträge:
    960
    Erhaltene Danke:
    262
    Registriert seit:
    16.11.2009
    Der hilft an der Stelle vermutlich nicht viel. Die Exception ist direkt an der Stelle ohne "Zwischenklassen", danach kommt der übliche Kram bis zum Aufruf, z.B.
    Code:
    java.lang.ArrayIndexOutOfBoundsException
        de.stohelit.folderplayer.playback.FolderManager.fillShuffleAll(FolderManager.java:1686)
        de.stohelit.folderplayer.playback.FolderManager.gotoTrack(FolderManager.java:1137)
        de.stohelit.folderplayer.playback.PlaybackService$7.gotoTrack(PlaybackService.java:1592)
        de.stohelit.folderplayer.TrackList$7.onClick(TrackList.java:427)
        com.android.internal.app.AlertController$AlertParams$3.onItemClick(AlertController.java:876)
        ....
     
  7. Blalasaadri2, 08.10.2010 #7
    Blalasaadri2

    Blalasaadri2 Android-Hilfe.de Mitglied

    Beiträge:
    61
    Erhaltene Danke:
    15
    Registriert seit:
    05.10.2010
    Phone:
    Motorola Milestone
    Ich kenne mich zwar mit Android-Java noch nicht aus, aber in "normalem" Java (J2SE) würde ich einfach mal ein
    Code:
    System.out.println("[FONT=monospace]filesDeck.size() = [/FONT]" + filesDeck.size() 
                     + ", foldersDeck.size() = " + foldersDeck.size() 
                     + ", pos = " + pos);
    nach der Änderung der pos-Variable einfügen und schauen, bei welchen Werten diese Exception kommt. Erfahrungsgemäß vertut man sich da gern mal um 1.

    Gruß,
    Blalasaadri
     
  8. Kranki, 08.10.2010 #8
    Kranki

    Kranki Ehrenmitglied

    Beiträge:
    3,831
    Erhaltene Danke:
    814
    Registriert seit:
    19.07.2009
    Tablet:
    Samsung Galaxy Tab 3 7.0 Lite
    Ist die erste for-Schleife sehr komplex oder geheim? Ich seh da nämlich ein Array in dem Ausschnitt, den du gepostet hast, und die beiden in der zweiten Schleife würd ich fast ausschließen.
    Code:
    for ( alle Dateien in den ersten, zufälligen Ordnern ) {
        foldersDeck.add( shuffleFolders[i] );
        filesDeck.add( ii );
    }
     
  9. Mort, 10.10.2010 #9
    Mort

    Mort Threadstarter Android-Lexikon

    Beiträge:
    960
    Erhaltene Danke:
    262
    Registriert seit:
    16.11.2009
    Ne, das nicht. Nur etwas verwirrend, und eigentlich geht's an der Stelle ja nur darum, dass die beiden Deck-Arrays gleichzeitig an derselben Stelle gefüllt werden.

    Code:
            fillShuffleFolders(); // füllt shuffleFolders mit den Ordner-Indizes in zufälliger Reihenfolge. Nach dem Füllen der Decks wird dieser Array "weggeworfen" (out of scope via folderArray = new ...)
    
            for ( int i = 0; i < shuffleFolders.length && foldersDeck.size() < maxFilesForShuffleAll*2; i++ ) {
                FolderInfo folder = foldersWithFiles.get( shuffleFolders[i] );
                for ( int ii = 0; ii < folder.getPlayableFiles(); ii++ ) {
                    // aktuelles und nächstes File werden hinterher
                    // an den Anfang verfrachtet, deshalb hier ignoieren
                    if ( ( shuffleFolders[i] != currentFolderIndex 
                            || ii != currentFileIndex )
                        && ( nextFileIndex == -1
                                || shuffleFolders[i] != nextFolderIndex 
                                || ii != nextFileIndex )
                        ) {
                        foldersDeck.add( shuffleFolders[i] );
                        filesDeck.add( ii );
                    }
                }
            }
    
     

Diese Seite empfehlen