Avatar billede mmmap Nybegynder
18. december 2009 - 16:16 Der er 11 kommentarer og
1 løsning

Parse .CSV fil hurtigere

Hej! Jeg er ved at lave en stump kode som parser en semikolonsepareret fil på 1.1 mb (22.000 linier). I filen står der blandt andet nogle koordinater (i UTM32 format) som jeg skal konvertere til almindelig bredde- og længdegrad, og derefter udregne afstanden mellem til den opgivede Location. Derefter skal de lægges i en ArrayList, hvis afstanden er under X meter. Problemet er dog, at det tager ca. 10 minutter at parse filen, og det er lige lang tid nok, synes jeg :-)

Hvordan kan jeg få tempoet lidt op? Min nuværende kode er følgende:

    public ArrayList<Station> getBusStations(Location loc, InputStream mFile) {
        try {
            BufferedReader br = new BufferedReader(new InputStreamReader(mFile));
            ArrayList<Station> stations = new ArrayList<Station>();
            CoordinateConversion converter = new CoordinateConversion();
            //Første linie skal læses da denne ikke
            //indeholder brugbar info
            br.readLine();
            String strLine;
            while ((strLine = br.readLine()) != null) {
                String[] ln = strLine.split(";");
               
                //Konverterer fra UTM32 til lat/lon
                double[] latlon = converter.utm2LatLon("32 N " + ln[2] + " "
                        + ln[3]);
                //Undersøger dinstancen og putter længden i
                // et float (fl)               
                float[] fl = new float[1];
                Location.distanceBetween(loc.getLatitude(), loc.getLongitude(),
                        latlon[0], latlon[1], fl);
                if (((int) fl[0]) < 1000) {
                    stations.add(new Station(latlon[0], latlon[1], ln[1]));
                }
            }
            mFile.close();
            return stations;
        } catch (IOException e) {
            e.printStackTrace();
        }
        return null;
    }


Mvh. Mads
Avatar billede arne_v Ekspert
18. december 2009 - 16:35 #1
Jeg mistaenker at meget af tiden bliver brugt i converter.utm2LatLon.

Location.distanceBetween kunne nok med fordel aendres til at returnere en float fremfor at sende et array med 1 element over.
Avatar billede arne_v Ekspert
18. december 2009 - 16:46 #2
Maaske kunne hele afstands testet optimeres.

(x2 - x1)^2 + (y2 - y1)^2 < z^2

er meget hurtigere end:

sqrt((x2 - x1)^2 + (y2 - y1)^2) < z
Avatar billede mmmap Nybegynder
18. december 2009 - 19:42 #3
Hej, og tak for svarene!

Jeg har testet lidt, og som du tror er det converter.utm2latLon der tager lang tid. Det kunne være, at man skulle omregne den opgivede position til UTM fremfor de andre 22.000. Jeg prøvede at ændre afstands testen og det gav vist nok lidt. Det varer dog stadig omkring 7 minutter, hvilket virker lidt voldsomt. Men jeg vil prøve at omregne den opgivede position til UTM og sammenligne dem derefter.
Avatar billede arne_v Ekspert
18. december 2009 - 19:52 #4
Du kunne formentligt spare en del ved bare at aendre utm2LatLon til ikke at sende en streng med over som argument med sende de enkelte dele over.
Avatar billede mmmap Nybegynder
18. december 2009 - 21:06 #5
Jeg har prøvet at kommenteret alt i lykken, bortset fra String[] ln = strLine.split(";") og dette i sig selv tager flere minutter at køre igennem. Jeg havde godt nok aldrig troet, at det tog så lang tid at parse en CSV fil. Men jeg vil prøve at gøre lykken hurtigere hvor jeg kan.

Eller er der noget helt andet der kan gøres for at få det til at gå hurtigere? Eventuelt kopiere dataen ind i en database før jeg udgiver den (filen vil blive opdateret på nettet engang i mellem) ?
Avatar billede arne_v Ekspert
18. december 2009 - 21:20 #6
String split er faktisk lidt tung i det.

Proev evt. med en gammeldags StringTokenizer.
Avatar billede mmmap Nybegynder
18. december 2009 - 21:36 #7
Det hjalp en hel del. Smid et svar, der er nok ikke så meget mere at gøre ved den, selvom jeg dog ikke er helt tilfreds med den tid, som den bruger :-)
Avatar billede arne_v Ekspert
18. december 2009 - 21:53 #8
svar
Avatar billede arne_v Ekspert
18. december 2009 - 21:54 #9
Kan du vise koden til utm2LatLon?
Avatar billede mmmap Nybegynder
18. december 2009 - 21:58 #10
Ja, selvfølgelig. Jeg har "nuppet" koden fra IBM, og det er vist lettest hvis du får linket hertil:

http://www.ibm.com/developerworks/java/library/j-coordconvert/index.html
Avatar billede arne_v Ekspert
18. december 2009 - 22:12 #11
Den laver ogsaa en split - hvis den kunne elimineres, saa kunne der nok spares en del igen.
Avatar billede mmmap Nybegynder
18. december 2009 - 22:34 #12
Det hjalp en smule mere. Mange tak!
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Kurser inden for grundlæggende programmering

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester