powered by simpleCommunicator - 2.0.61     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Java [игнор отключен] [закрыт для гостей] / Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
51 сообщений из 51, показаны все 3 страниц
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196572
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Всем привет.

Есть текст среднего размера, его надо разбить на слова и вывести затем эти слова в обратном порядке в новый файл.
То есть, для входного файла с таким содержимым:
Код: java
1.
2.
3.
4.
5.
6.
7.
abc bx      cde

e 
      fz  g


qwerty

- надо получить на выходе:
Код: java
1.
2.
3.
4.
5.
6.
7.
qwerty
g
fz
e
cde
bx
abc

Исходный файл небольшой: размер около 8 Мегов, содержит 149 тыс слов (язык - английский).

Полазив в интернетах, сделал следующий класс:
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
import java.io.*;
public class FileWordsReverser {
        public static void main(String[] args) throws IOException {

            BufferedReader br = null;
            StringBuilder sb = new StringBuilder();
            try {

                String xline;
                String[] words;

                System.out.println("start: "+System.currentTimeMillis());
                br = new BufferedReader(new FileReader("C:\\hugetext.txt"));
                while ((xline = br.readLine()) != null) {
                    //System.out.println(xline);
                    words = xline.split("\\s+");
                    for (int i = 0; i < words.length; i++) {
                        sb.append(words[i]).append("\n");
                    }
                }

                words = sb.toString().split("\\s+");

                File file = new File("C:\\hugetext.rev");

                if (!file.exists()) {
                    file.createNewFile();
                }

                FileWriter fw = new FileWriter(file.getAbsoluteFile());
                BufferedWriter bw = new BufferedWriter(fw);
                for (int i = words.length-1; i >= 0; i--) {
                    bw.write(words[i]+"\n");
                }
                bw.close();
                System.out.println("Finish: "+System.currentTimeMillis());

            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                try {
                    if (br != null) br.close();
                } catch (IOException ex) {
                    ex.printStackTrace();
                }
            }

    }
}

Он считывает весь файл и пишет слова в обратном порядке в новый файл за 7.5 сек (машина - старый PC, 2.4 GHz / 1GB RAM).
Однако расход памяти в пиковый момент достигает 117 мегов (для всего 8 мегов исходного текста).

Покритикуйте, плз, код: я вообще в ту степь полез или надо медитировать над другими способами ? Как уменьшить расход памяти ?
Сам текстовый файл тут: http://yadi.sk/d/5UsjXzJ-3VcUs

Заранее спасибо за ответы.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196652
Фотография Usman
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ozzmosis,

Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
BufferedReader istream = new BufferedReader(new FileReader("hugetext.txt"));
List<String> tokens = new ArrayList<String>();
while (istream.ready()) {
    for (String token: istream.readLine().split("\\s+")) {
        if (token.trim().length() > 0) {
            tokens.add(token);
        }
    }
}
istream.close();
BufferedWriter ostream = new BufferedWriter(new FileWriter("hugetext.rev"));
for (int i = tokens.size(); --i >= 0;) {
    ostream.write(tokens.get(i));
    ostream.write("\n");
    ostream.flush();
}
ostream.close();
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196654
Leonidv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Два момента:
1. У StringBuilder есть метод insert
2. StringBuilder вам не нужен. Начните с просто ArrayList и при считывание файла заполняйте его в обычном порядке. А вот уже при сохранение в файл делайте обход в обратном порядке. После заполнения arraylist вызовите list.trimToSize(), если вам важно съэкономить память. Этот метод есть только у ArrayList, т.е. переменная должна быть именно этого типа.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196688
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Usman, Leonidv - спасибо за ответы.

Только не взлетело :(
Вот два варианта через ArrayList, оба в пиковый момент всё равно жрут 120 мегов:
variant-1 : шустрый, 4.5 сек вместо прежних 7.5
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
import java.io.*;
import java.util.*;

public class FileWordsReverser2 {
    public static void main(String[] args) {
        ArrayList<String> aWords = new ArrayList<String>();
        String xline;
        String[] words;
        BufferedReader br;

        System.out.println("start:  "+System.currentTimeMillis());
        try {
            br = new BufferedReader(new FileReader("C:\\hugetext.txt"));
            try {
                while ((xline = br.readLine()) != null) {

                    words = xline.split("\\s+");
                    aWords.addAll(Arrays.asList(words));
                }
                br.close();
                //no effect in memory consumption:
                //aWords.trimToSize();

                File file = new File("C:\\hugetxt2.rev");

                if (!file.exists()) {
                    file.createNewFile();
                }

                FileWriter fw = new FileWriter(file.getAbsoluteFile());
                BufferedWriter bw = new BufferedWriter(fw);

                for (int i = aWords.size()-1; i >= 0; i--) {
                    bw.write( aWords.get(i) +"\n");
                }
                bw.close();
                System.out.println("Finish: "+System.currentTimeMillis());

            } catch (IOException ex) {
                ex.printStackTrace();
            }
        } catch (FileNotFoundException ex) {
            ex.printStackTrace();
        }
        //---------------------------------------------------------------------

    }
}

Output:
Код: plaintext
1.
2.
start:  1364152678296
Finish: 1364152682812

variant-2 (от Usman, чуток только подпиленный)
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
import java.io.*;
import java.util.*;
public class FileWordsReverser3 {
    public static void main(String[] args) {
        BufferedReader istream;
        List<String> tokens = new ArrayList<String>();

        System.out.println("Start:  "+System.currentTimeMillis());

        try {
        istream = new BufferedReader(new FileReader("c:\\hugetext.txt"));
            try {

                while (istream.ready()) {
                    for (String token: istream.readLine().split("\\s+")) {
                        if (token.trim().length() > 0) {
                            tokens.add(token);
                        }
                    }
                }
                istream.close();

                BufferedWriter ostream = new BufferedWriter(new FileWriter("c:\\hugetxt3.rev"));
                for (int i = tokens.size(); --i >= 0;) {
                    ostream.write(tokens.get(i));
                    ostream.write("\n");
                    ostream.flush();
                }
                ostream.close();

            } catch (IOException ex) {
                ex.printStackTrace();
            }
       } catch (FileNotFoundException ex) {ex.printStackTrace();}

       System.out.println("Finish: "+System.currentTimeMillis());

    }

}

Этот вариант медленнее первоначального:
Код: plaintext
1.
Start:  1364152777984
Finish: 1364152791375

Но самая печалька в том, что все три варианта (первый и эти два) жрут одинаково: около 120 мегов (в аттаче - картинка при запуске var_1).
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196691
rdm
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Это случайно не с T system задание? )
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196699
Leonidv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Подключите профайлер (visualvm, например) и через него смотрите, что происходит. Попробуйте запустить JVM с ограничением по памяти.

Код: java
1.
2.
3.
               
 //no effect in memory consumption:
//aWords.trimToSize();


Так и не должно было быть. Этот прием применяется в том случае, если вам надо обрабатывать данные параллельно и на самом деле важен каждый килобайт. Суть в том, что пиковый размер выделяемой памяти данный метод не меняет, но после его вызова памяти может начать выделяться. Насколько меньше - зависит от размера массива. См. capacity и load factor.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196706
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
rdmЭто случайно не с T system задание? )Нет :-)
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196711
Фотография Паша01
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Я в Джаве новичок, так что не орите
, но разве LinkedList не лучше ArrayList, ведь первый оптимизирован для последовательных доступов, т.к. является связанным списком.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196712
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
LeonidvПодключите профайлер (visualvm, например) и через него смотрите, что происходит. Попробуйте запустить JVM с ограничением по памяти.А как ограничить JVM ?
Пытаюсь, но не получается:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
D:\JAVA\1Probe>java -Xmx:64m FileWordsReverser2
Invalid maximum heap size: -Xmx:64m
Could not create the Java virtual machine.

D:\JAVA\1Probe>java -Xmx:96m FileWordsReverser2
Invalid maximum heap size: -Xmx:96m
Could not create the Java virtual machine.

D:\JAVA\1Probe>java -Xmx:128m FileWordsReverser2
Invalid maximum heap size: -Xmx:128m
Could not create the Java virtual machine.

D:\JAVA\1Probe>java -Xmx:256m FileWordsReverser2
Invalid maximum heap size: -Xmx:256m
Could not create the Java virtual machine.

А дока вообще говорит, что:
-X Command-line options
Код: plaintext
1.
2.
3.
-Xmx

This option sets the maximum Java heap size. The Java heap (the “heap”) is the part of the memory where blocks of memory are allocated to objects and freed during garbage collection. Depending upon the kind of operating system you are running, the maximum value you can set for the Java heap can vary.
Note: 	 -Xmx does not limit  the total amount of memory that the JVM can use.


PS.
D:\JAVA\1Probe>java -version
java version "1.6.0_31"
Java(TM) SE Runtime Environment (build 1.6.0_31-b05)
Java HotSpot(TM) Client VM (build 20.6-b01, mixed mode, sharing)
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196713
Фотография Паша01
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
А ещё можно узнать, зачем копировать огромный текст в коллекцию? Я бы уже копался, пытаясь узнать, как считать текстовый файл с последней строки до первой. Тогда и не надо большие объемы памяти.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196716
Фотография Usman
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ozzmosis,

Как вариант, создайте локальную БД (типа SQLite) с одной таблицей и загоняйте туда последовательно все слова (вместо ArrayList'а)...
из БД доставайте при помощи запроса "SELECT ... ORDER BY ID DESC"
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196718
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
LeonidvПодключите профайлер (visualvm, например) и через него смотрите, что происходит.Просветите неуча: вот запустил я его, дальше запустил java myapp - и как его профилировать ? он (myapp) появляется на доли секунды в левой панели ("дереве" приложений) и тут же исчезает :/
Здесь читал, но там он "запустил фоном DaCapo:lusearch" - т.е. это приложение у него постоянно торчит в списке.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196719
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Паша01А ещё можно узнать, зачем копировать огромный текст в коллекцию? Я бы уже копался, пытаясь узнать, как считать текстовый файл с последней строки до первой. Тогда и не надо большие объемы памяти.ну так мне в конечном счете это и надо: прочитать текст "от обратного". Только я нигде не видел такого, чтобы файл "задом наперёд" читать можно было :-)
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196720
Фотография Usman
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ozzmosisТолько я нигде не видел такого, чтобы файл "задом наперёд" читать можно было :-)
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
File tempFile = File.createTempFile("HUGE", "TEXT");
tempFile.deleteOnExit();
BufferedReader istream1 = new BufferedReader(new FileReader("hugetext.txt"));
BufferedWriter ostream1 = new BufferedWriter(new FileWriter(tempFile));
while (istream1.ready()) {
    for (String token: istream1.readLine().split("\\s+")) {
        if (token.trim().length() > 0) {
            ostream1.write(token);
            ostream1.write("\n");
            ostream1.flush();
        }
    }
}
istream1.close();
ostream1.close();

RandomAccessFile istream2 = new RandomAccessFile(tempFile, "r");
BufferedWriter ostream2 = new BufferedWriter(new FileWriter("hugetext.rev"));
for (long pos = istream2.length() - 1; pos >= 0;) {
    StringBuilder word = new StringBuilder();
    for (byte ch = 0; ch != '\n' && --pos >= 0;) {
        istream2.seek(pos);
        ch = istream2.readByte();
        word.append((char)ch);
    }
    ostream2.write(word.reverse().toString().trim());
    ostream2.write("\n");
    ostream2.flush();
}
istream2.close();
ostream2.close();
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196721
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Usmanozzmosis,

Как вариант, создайте локальную БД (типа SQLite) с одной таблицей и загоняйте туда последовательно все слова (вместо ArrayList'а)...
из БД доставайте при помощи запроса "SELECT ... ORDER BY ID DESC"Спасибо, попробую. Но не с SQLite'ом, а с другой базой. Только есть смутное терзание, что по времени тоскливо станет.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196737
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Usman
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
...
for (long pos = istream2.length() - 1; pos >= 0;) {
    StringBuilder word = new StringBuilder();
    for (byte ch = 0; ch != '\n' && --pos >= 0;) {
        istream2.seek(pos);
        ch = istream2.readByte();
        word.append((char)ch);
    }

теперь с расходом памяти всё пучком (16 мегов), но время выполнения стало тихим кошмаром: 42 сек.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196788
Фотография Usman
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ozzmosis,

Должен быть выигрыш в несколько секунд:
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
RandomAccessFile istream = new RandomAccessFile("hugetext.txt", "r");
BufferedWriter ostream = new BufferedWriter(new FileWriter("hugetext.rev"));
for (long pos = istream.length() - 1; pos >= 0;) {
    StringBuilder line = new StringBuilder();
    for (byte ch = 0; ch != '\n' && --pos >= 0;) {
        istream.seek(pos);
        ch = istream.readByte();
        line.append((char)ch);
    }
    String[] words = line.reverse().toString().trim().split("\\s+");
    for (int i = words.length; --i >= 0;) {
        if (words[i].trim().length() > 0) {
            ostream.write(words[i].trim());
            ostream.write("\n");
        }
    }
}
ostream.flush();
istream.close();
ostream.close();
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196819
Leonidv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ozzmosisА как ограничить JVM ?
Пытаюсь, но не получается:

http://greenmice.info/ru/node/143
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196849
WGA
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
WGA
Гость
ozzmosis,

Все приведенные варианты решения так или иначе связаны с расширением массива символов, что затратно. Уж хотя бы StringBuilder'у сразу задайте размер побольше.

Или просто загнать весь файл в структуру char[]? А потом пройтись обычным циклом по всем элементам с нахождением слов. Тогда расход памяти не должен превышать размер входного файла, а проход по 8М байтов в памяти - сущий пустяк.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196875
ivanra
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
По-моему, напрашивается Memory Mapped file - совершенно необязательно весь файл зачитывать в память, достаточно отобразить его в память, и зачитывать оттуда небольшие кусочки, начиная с хвоста. Как-то так:
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
		int buffSize = 4096;
		byte[] buffer = new byte[buffSize];
		FileChannel fc = new RandomAccessFile("name", "r").getChannel();
		MappedByteBuffer in = fc.map(FileChannel.MapMode.READ_ONLY, 0, fc.size());
		int offset = (int)fc.size()-buffSize;
		while (offset>=0) { 
			in.get(buffer, offset, buffSize);
			// тут разбираем буфер на слова и записываем из в выходной файл, в обратном порядке
			// самое первое слово запоминаем, вдруг оно начинается в предыдущем буфере
			// в конце уменьшаем offset и buffSize, если надо
		}
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196917
Фотография Паша01
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
WGAИли просто загнать весь файл в структуру char[]?
Да вообще лучше без этого, а если файл под 1 Гб.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196930
am_sasa
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
ivanraзачитывать оттуда небольшие кусочки не вариант, можно слова порезать
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196942
Фотография grasoff.net
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ozzmosis
Код: plaintext
1.
2.
D:\JAVA\1Probe>java -Xmx:256m FileWordsReverser2
Invalid maximum heap size: -Xmx:256m
Could not create the Java virtual machine.
двоеточие лишнее
хотя леонидв намекнул об етом ссылкой
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38196954
eny
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
eny
Гость
ozzmosis,

хранить в списке нужно не слова, а целочисленные смещения курсора относительно начала файла, тогда потребуется обычный целый массив: читаем словечко, запоминаем смещение и тд и тп. ну и потом в обратном порядке проходим массив, позиционируем курсор и читаем до следующей позиции, как то-так

Зачем что-то кэшировать? Роль буфера вполне выполнит уже имеющийся файл.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197067
Фотография grasoff.net
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ozzmosisВсем привет.

Есть текст среднего размера, его надо разбить на слова и вывести затем эти слова в обратном порядке в новый файл.
То есть, для входного файла с таким содержимым:
Код: java
1.
2.
3.
4.
5.
6.
7.
abc bx      cde

e 
      fz  g


qwerty


- надо получить на выходе:
Код: java
1.
2.
3.
4.
5.
6.
7.
qwerty
g
fz
e
cde
bx
abc


Исходный файл небольшой: размер около 8 Мегов, содержит 149 тыс слов (язык - английский).

Полазив в интернетах, сделал следующий класс:
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
import java.io.*;
public class FileWordsReverser {
        public static void main(String[] args) throws IOException {

            BufferedReader br = null;
            StringBuilder sb = new StringBuilder();
            try {

                String xline;
                String[] words;

                System.out.println("start: "+System.currentTimeMillis());
                br = new BufferedReader(new FileReader("C:\\hugetext.txt"));
                while ((xline = br.readLine()) != null) {
                    //System.out.println(xline);
                    words = xline.split("\\s+");
                    for (int i = 0; i < words.length; i++) {
                        sb.append(words[i]).append("\n");
                    }
                }

                words = sb.toString().split("\\s+");

                File file = new File("C:\\hugetext.rev");

                if (!file.exists()) {
                    file.createNewFile();
                }

                FileWriter fw = new FileWriter(file.getAbsoluteFile());
                BufferedWriter bw = new BufferedWriter(fw);
                for (int i = words.length-1; i >= 0; i--) {
                    bw.write(words[i]+"\n");
                }
                bw.close();
                System.out.println("Finish: "+System.currentTimeMillis());

            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                try {
                    if (br != null) br.close();
                } catch (IOException ex) {
                    ex.printStackTrace();
                }
            }

    }
}


Он считывает весь файл и пишет слова в обратном порядке в новый файл за 7.5 сек (машина - старый PC, 2.4 GHz / 1GB RAM).
Однако расход памяти в пиковый момент достигает 117 мегов (для всего 8 мегов исходного текста).

Покритикуйте, плз, код: я вообще в ту степь полез или надо медитировать над другими способами ? Как уменьшить расход памяти ?
Сам текстовый файл тут: http://yadi.sk/d/5UsjXzJ-3VcUs] http://yadi.sk/d/5UsjXzJ-3VcUs

Заранее спасибо за ответы.

такто вощето надо
1. вместо list использовать Stack
2. в него класть строки, прочитанные из файла, без всяких сплитов
3. потом делать stack.pop().split()
4. и в обратном порядке писать етот массив в файл

скорость скорее всего не увеличится
используемая память уменьшится раза в два так наверняка
пасмари если не лень )
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197089
eny
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
eny
Гость
grasoff.net,

Те же сферические объекты, вид с боку, ЗАЧЕМ ВООБЩЕ файл грузить в ОЗУ целиком?

Не важно, как он логически будет разбиваться на объекты, в любом случае потребуется оперативка в размере файла, плюс всякие дополнительные данные для поддержки выбранной структуры классов. А если файл будет не 8 М а все 200 М и все - картина маслом.

Задача - отиндексировать файл по началу строк и полученный индекс разместить в фале или в массиве и по индексу в обратном порядке считывать одну строку из файла. Ресурсов ОЗУ - на одну строку с максимальной длинной. Плюс не надо генерить и инициализировать кучу сопутствующих объектов.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197095
Фотография Blazkowicz
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
enyТе же сферические объекты, вид с боку, ЗАЧЕМ ВООБЩЕ файл грузить в ОЗУ целиком?

Традиционная оптимизация. Чтобы достичь максимальной эффективности работы CPU, нужно свести IO к минимуму, загрузива данные в память. Вот только структура нужна оптимальная для задачи.

enyЗадача - отиндексировать файл по началу строк и полученный индекс разместить в фале или в массиве и по индексу в обратном порядке считывать одну строку из файла. Ресурсов ОЗУ - на одну строку с максимальной длинной. Плюс не надо генерить и инициализировать кучу сопутствующих объектов.
Индексирование тоже дополнительные ресурсы.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197116
Озверин
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Почему нельзя читать файл с конца и сразу писать в новый файл?
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197173
Лагман
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ОзверинПочему нельзя читать файл с конца и сразу писать в новый файл?
i second this.
also можно читать/писать например буфером N КБайтов, будет и быстро и памяти около нуля.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197187
Фотография ПЕНСИОНЕРКА
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ozzmosis,

авторсодержит 149 тыс слов (язык - английский).
слов всего 1,500,000
слов без повторов 28307
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197518
bajork
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
RandomAccessFile istream = new RandomAccessFile("1.log", "r");
BufferedWriter ostream = new BufferedWriter(new FileWriter("1_new.log"));
 
long len = istream.length() - 1;
 
istream.seek(len);
byte ch = istream.readByte();
 
char [] buff = new char[255];
 
for (long pos = len - 1; pos > 0;) {
 while (pos >= 0 && ch < 33) {
  istream.seek(--pos);
  ch = istream.readByte();
 }
 	
 int idx = 0;
 while (pos > 0 && ch > 32) {
  buff[idx++] = (char)ch;
  istream.seek(--pos);
  ch = istream.readByte();
 }
 	
 if (idx != 0) {
  for (int i = idx; --i >= 0; )
   ostream.write(buff[i]);
  	
  ostream.write("\n");
 }
}
 
ostream.flush();
istream.close();
ostream.close();


;)
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197529
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
WGAИли просто загнать весь файл в структуру char[]? А потом пройтись обычным циклом по всем элементам с нахождением слов. Тогда расход памяти не должен превышать размер входного файла, а проход по 8М байтов в памяти - сущий пустяк.Да, но размер char-массива - его ведь тогда заранее надо задать ?
grasoff.net 1. вместо list использовать Stack
<...>
скорость скорее всего не увеличится
используемая память уменьшится раза в дваОтличный совет, большое спасибо! Именно так и получилось: память уменьшилась до 55 мегов (т.е. в два с небольшим раза), скорость возросла: стало 3 секунды вместо 4.5 для ArrayList'a.
Одного понять не могу: итерация по стеку должна ВСЕГДА идти вроде как в LIFO-порядке ? Если так, то странно как-то:
Код: java
1.
2.
3.
4.
5.
for(String s : sWords) {
    String[] a = s.split("\\s+");
    for (int i = a.length-1; i >= 0; i--) {
        bw.write( a[i] +"\n");
    }

- обрабатывает строки, начиная с "дна" стека, а не с его вершины.
Пришлось через while делать:
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
import java.io.*;
import java.util.*;
public class FileWordsReverserStack {
    public static void main(String[] args) throws IOException {
        Stack<String> sWords = new Stack<String>();
        String xline;
        BufferedReader br;

//        System.out.println("\n\nPress Enter to begin...");  
//        System.in.read();  
        System.out.println("Start:  "+System.currentTimeMillis());
        try {
            br = new BufferedReader(new FileReader("C:\\hugetext.txt"));
            try {
                while ((xline = br.readLine()) != null) {
                    sWords.push(xline);
                    //words = xline.split("\\s+");
                    //aWords.addAll(Arrays.asList(words));
                }
                br.close();

                File file = new File("C:\\ht_Stack.rev");

                if (!file.exists()) {
                    file.createNewFile();
                }

                FileWriter fw = new FileWriter(file.getAbsoluteFile());
                BufferedWriter bw = new BufferedWriter(fw);
                
                while (!sWords.empty()) {
                    String[] a = sWords.pop().split("\\s+");
                    for (int i = a.length-1; i >= 0; i--) {
                        bw.write( a[i] +"\n");
                    }    
                }
// order of iteration is FIFO rather than LIFO!
//                for(String s : sWords) {
//                    String[] a = s.split("\\s+");
//                    for (int i = a.length-1; i >= 0; i--) {
//                        bw.write( a[i] +"\n");
//                    }
//                }
                bw.close();
                System.out.println("Finish: "+System.currentTimeMillis());
//                System.out.println("\n\nPress Enter to continue...");  
//                System.in.read();  

            } catch (IOException ex) {
                ex.printStackTrace();
            }
        } catch (FileNotFoundException ex) {
            ex.printStackTrace();
        }
        //---------------------------------------------------------------------

    }
}
/*
Start:  1'364'212'829'904
Finish: 1'364'212'833'122 
*/
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197552
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
bajork
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
RandomAccessFile istream = new RandomAccessFile("1.log", "r");
BufferedWriter ostream = new BufferedWriter(new FileWriter("1_new.log"));
 
long len = istream.length() - 1;

istream.seek(len);
byte ch = istream.readByte();
 
char [] buff = new char[255];
 
for (long pos = len - 1; pos > 0;) {
 while (pos >= 0 && ch < 33) {
  istream.seek(--pos);
  ch = istream.readByte();
 }
<...>

Памяти действительно только 8 мегов расходовало, но:
Код: plaintext
1.
2.
Start:  1364214553747
Finish: 1364214593466
BUILD SUCCESSFUL (total time: 40 seconds)
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197609
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
ozzmosisОдного понять не могу: итерация по стеку должна ВСЕГДА идти вроде как в LIFO-порядке ?Нарыл, вопрос снят.
Попробовал до кучи ArrayDeque, в доке говорится , что онClass ArrayDeque<E>is likely to be faster than Stack when used as a stack- но нет, те же самые 55 мегов и 3.2...3.5 секунды.
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
import java.io.*;
import java.util.*;
public class FileWordReverserArrayDeque {
    public static void main(String[] args) throws IOException {
        //Stack<String> sWords = new Stack<String>();
        ArrayDeque<String> dWords = new ArrayDeque<String>();
        String xline;
        BufferedReader br;

//        System.out.println("\n\nPress Enter to begin...");  
//        System.in.read();  
        System.out.println("Start:  "+System.currentTimeMillis());
        try {
            br = new BufferedReader(new FileReader("C:\\hugetext.txt"));
            try {
                while ((xline = br.readLine()) != null) {
                    dWords.add(xline);
                    //sWords.push(xline);
                }
                br.close();

                File file = new File("C:\\ht_ADeque.rev");

                if (!file.exists()) {
                    file.createNewFile();
                }

                FileWriter fw = new FileWriter(file.getAbsoluteFile());
                BufferedWriter bw = new BufferedWriter(fw);
                
                for(Iterator<String> id = dWords.descendingIterator(); id.hasNext(); ) {
                    String[] a = id.next().split("\\s+");
                    for (int i = a.length-1; i >= 0; i--) {
                        bw.write( a[i] +"\n");
                    }    
                }
                
//                while (!dWords.isEmpty() ) {
//                    String[] a = dWords.pollLast().split("\\s+");
//                    for (int i = a.length-1; i >= 0; i--) {
//                        bw.write( a[i] +"\n");
//                    }    
//                }

                bw.close();
                System.out.println("Finish: "+System.currentTimeMillis());
//                System.out.println("\n\nPress Enter to continue...");  
//                System.in.read();  

            } catch (IOException ex) {
                ex.printStackTrace();
            }
        } catch (FileNotFoundException ex) {
            ex.printStackTrace();
        }
          
    }
}

...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197619
bajork
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
RandomAccessFile istream = new RandomAccessFile("1.log", "r");
BufferedWriter ostream = new BufferedWriter(new FileWriter("1_new.log"));

MappedByteBuffer in = istream.getChannel().map(FileChannel.MapMode.READ_ONLY, 0, istream.length());
 
int len = (int)istream.length() - 1;
 
istream.seek(len);
byte ch = istream.readByte();
 
char [] buff = new char[255];
 
for (int pos = len - 1; pos > 0;) {
 while (pos >= 0 && ch < 33) {
  ch = in.get(--pos);
 }
 	
 int idx = 0;
 while (pos > 0 && ch > 32) {
  ch = in.get(--pos);
 }
 	
 if (idx != 0) {
  for (int i = idx; --i >= 0; )
   ostream.write(buff[i]);
  	
  ostream.write("\n");
 }
}
 
ostream.flush();
istream.close();
ostream.close();


?
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197633
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
bajork
Код: java
1.
2.
3.
4.
5.
RandomAccessFile istream = new RandomAccessFile("1.log", "r");
BufferedWriter ostream = new BufferedWriter(new FileWriter("1_new.log"));

MappedByteBuffer in = istream.getChannel().map(FileChannel.MapMode.READ_ONLY, 0, istream.length());
<...>

работает очень быстро, 0 сек. Только файл-результат тоже почему-то... нулевого размера
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197644
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
BufferedReader(..., int sz): какой по дефолту размер буфера у этого класса ? я вот поигрался со значениями 512, 1024, ..., 65536, 131072 - и не вижу во времени выполнения никакой разницы вообще. Всё те же 3 секунды (для ArrayDeque).
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197650
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
ozzmosisТолько файл-результат тоже почему-то... нулевого размера на всякий случай, вот код (файл c:\hugetext - существует и имеет размер 8338665 байт):
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
import java.io.*;
import java.nio.MappedByteBuffer;
import java.nio.channels.FileChannel;
public class FileWordsReverserBackwardRead {
    public static void main(String[] args) throws IOException {
        RandomAccessFile istream = new RandomAccessFile("c:\\hugetext.txt", "r");
        BufferedWriter ostream = new BufferedWriter(new FileWriter("c:\\ht_bkscan2.rev"));
        System.out.println("Start:  "+System.currentTimeMillis());

        MappedByteBuffer in = istream.getChannel().map(FileChannel.MapMode.READ_ONLY, 0, istream.length());

        int len = (int)istream.length() - 1;

        istream.seek(len);
        byte ch = istream.readByte();

        char [] buff = new char[255];

        for (int pos = len - 1; pos > 0;) {
         while (pos >= 0 && ch < 33) {
          ch = in.get(--pos);
         }

         int idx = 0;
         while (pos > 0 && ch > 32) {
          ch = in.get(--pos);
         }

         if (idx != 0) {
          for (int i = idx; --i >= 0; )
           ostream.write(buff[i]);

          ostream.write("\n");
         }
        }

        ostream.flush();
        istream.close();
        ostream.close();        
        
        System.out.println("Finish: "+System.currentTimeMillis());
    }
}

...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197661
bajork
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
ozzmosis,

строчку buff[idx++] = (char)ch; удалил ;)
надо было закопипастить...

кстати размер памяти можно понизить делая сброс буфера записи но при этом повысится время...
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197691
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
bajorkстрочку buff[idx++] = (char)ch; удалил ;)
надо было закопипастить...

кстати размер памяти можно понизить делая сброс буфера записи но при этом повысится время...В общем, рекорд: 1 сек!
Правда, проглатывает лишние пустые строки, а также в первом слове (в ИСХОДНОМ тексте; в новом оно будет последним) удаляет первую букву. Например, для текста:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
The First Book of Moses:  Called Genesis




1:1 In the beginning God created the heaven and the earth.

1:2 And the earth was without form, and void; and darkness was upon
the face of the deep. And the Spirit of God moved upon the face of the
waters.



1:3 And God said, Let there be light: and there was light.
- Ваш вариант выдаст:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
 ligh. 
was
there
and
light:
be
there
Let
said,
God
And
1:3
waters.
the
of
face
the
upon
moved
God
of
Spirit
the
And
deep.
the
of
face
the
upon
was
darkness
and
void;
and
form,
without
was
earth
the
And
1:2
earth.
the
and
heaven
the
created
God
beginning
the
In
1:1
Genesis
Called
Moses:
of
Book
First
 he 

Но это уже мелочи, поправимо. Большое спасибо за наводку!
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197848
Йуный джавистЪ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Не могли бы вы попробовать
Код: sql
1.
tac -r -s '\b' file.txt | sed  -r -e 's/\s+/\n/g' | sed -re '/^$/d'
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197949
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Йуный джавистЪ,

я же дал выше ссцылку на файл, что мешает Вам это сделать ?
(просто меня интересовало эффективное решение именно на яве)
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38197963
Йуный джавистЪ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Ява в 30 раз быстрее, хотя сравнивать не совсем корректно, потому что решение на шелле обладает большей функциональностью (умеет юникод).
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38198311
Озверин
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Йуный джавистЪЯва в 30 раз быстрее, хотя сравнивать не совсем корректно, потому что решение на шелле обладает большей функциональностью (умеет юникод).

Скажите мне кто-нибудь, о чем это сообщение?
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38198919
chabapok
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
если больших файлов не планируется, делаем так: читаем все 8мб в charbuffer, а потом перебирая его с конца ловим слова и печатаем каждую такую charsequence.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38198937
ozzmosis
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
chabapokесли больших файлов не планируется, делаем так: читаем все 8мб в charbuffer, а потом перебирая его с конца ловим слова и печатаем каждую такую charsequence.Если я правильно понял вот это:bajork
Код: java
1.
MappedByteBuffer in = istream.getChannel().map(FileChannel.MapMode.READ_ONLY, 0, istream.length());

- а также разъяснение доки: http://docs.oracle.com/javase/7/docs/api/java/nio/MappedByteBuffer.html
Код: plaintext
1.
2.
3.
public abstract class  MappedByteBuffer 
extends ByteBuffer

A direct byte buffer whose content is a memory-mapped region of a file. 
- код bajork'a так и делает.
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38198979
ivanra
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
ozzmosischabapokесли больших файлов не планируется, делаем так: читаем все 8мб в charbuffer, а потом перебирая его с конца ловим слова и печатаем каждую такую charsequence.bajork
Код: java
1.
MappedByteBuffer in = istream.getChannel().map(FileChannel.MapMode.READ_ONLY, 0, istream.length());


Это разные вещи. В первом случае - чтение файла в память (в кучу), во втором - отображение файла в память (средствами ОС, память в куче не выделяется).
Тут, чтобы понять разницу, надо читать не javadoc, а что-нибудь по операционке, например, Джеффри Рихтер. "Windows для профессионалов"
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38201916
superstealth
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Сильно извиняюсь, что влез, но м/б после этого post(а)
кому-нибудь захочется помедитировать на Питоне...


камень i5 2.67Ггц.

Расход памяти ~8Мег.
Скорость выполнения на:
Python 2.7 - 0.9сек.
Python 3.2 - 2.8сек.
Python 3.3 - 3.9сек.
Pypy 2.0beta - 2.3сек.
А для Cython(а) тут нечего оптимизировать.


Код, в среднем, получается короче в 3 раза, как по горизонтали, так и по вертикали.


Код: python
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
import time

filer = open('hugetext.txt')
filew = open('hugetext_1.txt','w')

t1 = time.clock()

k = filer.readlines()
k.reverse()
for i in k:
    for j in reversed(i.split()):
        filew.write( j + '\n' )

t2 = time.clock()
print( "прошло %0.10f" % ((t2 - t1)))

filew.close()
...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38206166
avp.mk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
superstealthпомедитировать
Intel Celeron B815 @ 1.60GHz, Java 7, WinXP
Время: 0.281 сек.

Думаю можно ещё ускорить, но лень.
Генератор
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
package textgen;

import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.nio.charset.Charset;
import java.util.Random;

public class TextGen {

    private static final String PATH_SRC = "C:\\Documents and Settings\\User\\Рабочий стол\\src.txt";
    private static final Charset CHARSET = Charset.forName("Cp1251");

    public static void main(String[] args) throws FileNotFoundException, IOException {
        FileOutputStream fos = new FileOutputStream(PATH_SRC);
        OutputStreamWriter osw = new OutputStreamWriter(fos, CHARSET);
        Random r = new Random(System.currentTimeMillis());
//        for (int i = 1; i < 50_000_001; ++i) { //650Mb
        for (int i = 1; i < 710_001; ++i) { //8Mb
            osw.write("слово");
            osw.write(Integer.toString(i));
            osw.write(r.nextBoolean() ? " " : "\n");
        }
        osw.flush();
    }
}

Сам
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
73.
74.
75.
76.
77.
78.
79.
80.
81.
82.
83.
package textparse;

import java.io.BufferedOutputStream;
import java.io.Closeable;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.RandomAccessFile;
import java.nio.MappedByteBuffer;
import static java.nio.channels.FileChannel.MapMode.READ_ONLY;

public class TextParse {

    private static final String
            PATH_SRC = "C:\\Documents and Settings\\User\\Рабочий стол\\src.txt",
            PATH_OUT = "C:\\Documents and Settings\\User\\Рабочий стол\\out.txt";
    private static final byte SEPARATOR[] = {0xD, 0xA};

    public static void main(String[] args) throws FileNotFoundException, IOException {
        long timeStart = System.currentTimeMillis();

        RandomAccessFile randomAccessFile = null;
        BufferedOutputStream os = null;
        try {
            randomAccessFile = new RandomAccessFile(PATH_SRC, "r");
            os = new BufferedOutputStream(new FileOutputStream(PATH_OUT));

            MappedByteBuffer mbb = randomAccessFile.getChannel().map(READ_ONLY, 0, randomAccessFile.length());
            int size = (int) randomAccessFile.length() - 1;

            byte[] buffer = new byte[64000];
            int position = 0, length = 0;

            for (int i = size - 1; i > -1; --i) {
                byte b = mbb.get(i);
                if (b > 32 || b < 0) {
                    position = i;
                    ++length;
                } else if (length > 0) {
                    mbb.position(position);
                    mbb.get(buffer, 0, length);

                    os.write(buffer, 0, length);
                    os.write(SEPARATOR);
                    length = 0;
                }
            }

            if (length > 0) {
                mbb.position(position);
                mbb.get(buffer, 0, length);
                os.write(buffer, 0, length);
            }

            os.flush();


            long timeFinish = System.currentTimeMillis();

            System.out.print("Время: ");
            System.out.print((timeFinish - timeStart) / 1000d);
            System.out.println(" сек.");
        } finally {
            closeResource(randomAccessFile, os);
        }
    }

    public static void closeResource(AutoCloseable... resources) {
        for (AutoCloseable resource : resources) {
            if (resource != null) {
                try { resource.close(); } catch (Exception e) {}
            }
        }
    }

    public static void closeResource(Closeable... resources) {
        for (Closeable resource : resources) {
            if (resource != null) {
                try { resource.close(); } catch (Exception e) {}
            }
        }
    }
}

...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38206811
avp.mk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Ошибся. Лишний раз -1 сделал.
Так правильно
Код: java
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
73.
74.
75.
76.
77.
78.
79.
80.
package textparse;

import java.io.BufferedOutputStream;
import java.io.Closeable;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.RandomAccessFile;
import java.nio.MappedByteBuffer;
import static java.nio.channels.FileChannel.MapMode.READ_ONLY;

public class TextParse {
    
    private static final String
            PATH_SRC = "C:\\Documents and Settings\\User\\Рабочий стол\\src.txt",
            PATH_OUT = "C:\\Documents and Settings\\User\\Рабочий стол\\out.txt";
    private static final byte SEPARATOR[] = {0xD, 0xA};
    
    public static void main(String[] args) throws FileNotFoundException, IOException {
        long timeStart = System.currentTimeMillis();
        
        RandomAccessFile randomAccessFile = null;
        BufferedOutputStream os = null;
        try {
            randomAccessFile = new RandomAccessFile(PATH_SRC, "r");
            os = new BufferedOutputStream(new FileOutputStream(PATH_OUT));
            MappedByteBuffer mbb = randomAccessFile.getChannel().map(READ_ONLY, 0, randomAccessFile.length());
            
            byte[] buffer = new byte[64000];
            int position = 0, length = 0;
            
            for (int i = (int) (randomAccessFile.length() - 1); i > -1; --i) {
                byte b = mbb.get(i);
                if (b > 32 || b < 0) {
                    position = i;
                    ++length;
                } else if (length > 0) {
                    mbb.position(position);
                    mbb.get(buffer, 0, length);
                    os.write(buffer, 0, length);
                    os.write(SEPARATOR);
                    length = 0;
                }
            }
            
            if (length > 0) {
                mbb.position(position);
                mbb.get(buffer, 0, length);
                os.write(buffer, 0, length);
            }
            
            os.flush();
            
            
            long timeFinish = System.currentTimeMillis();
            
            System.out.print("Время: ");
            System.out.print((timeFinish - timeStart) / 1000d);
            System.out.println(" сек.");
        } finally {
            closeResource(randomAccessFile, os);
        }
    }
    
    public static void closeResource(AutoCloseable... resources) {
        for (AutoCloseable resource : resources) {
            if (resource != null) {
                try { resource.close(); } catch (Exception e) {}
            }
        }
    }
    
    public static void closeResource(Closeable... resources) {
        for (Closeable resource : resources) {
            if (resource != null) {
                try { resource.close(); } catch (Exception e) {}
            }
        }
    }
}

...
Рейтинг: 0 / 0
Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
    #38207665
Фотография Паша01
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Спортсмен)
...
Рейтинг: 0 / 0
51 сообщений из 51, показаны все 3 страниц
Форумы / Java [игнор отключен] [закрыт для гостей] / Парсинг .txt-файла размером 8Мб (разбивка на слова): жрёт ~120 Мб памяти
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]