Исключение нехватки памяти в Android, когда HTML освобождает строку - PullRequest
1 голос
/ 22 мая 2011

Мне нужно, чтобы HTML расшифровал строку (HTML-файл, который избежал HTML (поэтому все значения в моей строке - & lt; TAG & gt; val & lt; / TAG & gt; и т. Д.), Размер ~ 1,4 МБ, чтобы я могиспользовать неэкранированный XML-код в синтаксическом анализаторе)

Проблема, с которой я сталкиваюсь, заключается в том, что я всегда получаю исключение нехватки памяти при попытке получить неэкранированную строку при использовании StringEscapeUtils.unescapeHtml (String)(библиотека apache-commons-lang-2.6).

Я также попробовал метод базового Android-API для удаления строки, но помимо того факта, что он был чертовски медленным, исключение нехватки памяти даже происходило с меньшимиStrings (~ 700kb).

Может кто-нибудь предложить мне, как я могу обработать такое преобразование String, не сталкиваясь с исключением из-за нехватки памяти?

1 Ответ

1 голос
/ 22 мая 2011

У Java есть несколько хороших основных возможностей, чтобы сделать это действительно просто. В приведенном ниже решении используется регулярное выражение для просмотра содержимого и замены символов. Для этого решения требуется выполнить небольшую работу, поскольку вам необходимо предоставить коды перехода. Вы можете найти список кодов перехода здесь [http://www.w3.org/TR/html4/sgml/entities.html][1] или в Интернете для других.

Вот код ниже:

import java.util.regex.*;
import java.util.*;

public class HtmlUnescape {
    public static void main(String[] args){
        HashMap<String,String> codes = new HashMap<String,String>();
        codes.put("&lt;", "<");
        codes.put("&gt;", ">");
        codes.put("&#34;", "\"");

        String html = "&lt;html&gt;&lt;head&gt;&lt;title&gt;Hello&lt;/title&gt;&lt;/head&gt;&lt;body&gt;&lt;h1&gt;The great escape &#34;example&#34;&lt;/h1&gt;&lt;/body&gt;&lt;/html&gt;";

        Matcher matcher = Pattern.compile("&#*\\w\\w\\w?\\w?;").matcher(html);
        StringBuffer matchBuffer = new StringBuffer();
        while(matcher.find()){
            matcher.appendReplacement(matchBuffer, codes.get(matcher.group()));
        }
        matcher.appendTail(matchBuffer);
        System.out.println (matchBuffer.toString());
    }
}

Что происходит в коде:

  • Сначала хеш хранит коды в unescape.
  • Во-вторых, переменная html хранит экранирующий HTML для обработки.
  • Далее мы используем выражение регулярного выражения для поиска и замены экранированных кодов, используя:
    • Matcher.find (),
    • Matcher.appendReplacement () и
    • Методы Matcher.appendTail ().

Попробуй это. Я не имею представления о производительности больших файлов, таких как ваш. Но код достаточно прост, чтобы его можно было настроить для достижения желаемой производительности.

...