Блокировка потоков с помощью Android ADK - PullRequest
1 голос
/ 24 февраля 2012

Я пытаюсь прочитать байты из InputStream аксессуара, не блокируя поток (если это возможно).

Как правило, я бы обернул вызов read(buffer) в if available(), однако available () выдает исключение (даже если read () отлично работает на InputStream).

Существуют ли другие решения, которые минимизируют блокировку потоков?

EDIT:

Я настроил AsyncTask для чтения в фоновом режиме (хотя я знаю, что для расширенной задачи я должен использовать реальный поток), и он отлично работает.

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

Может ли BufferedInputStream уменьшить нагрузку на всех? У него есть собственный метод available ().

Ответы [ 2 ]

1 голос
/ 24 февраля 2012

В ответ на ваш отредактированный вопрос нет, производительность не снижается из-за блокировки фонового потока при вызове read().По сути, это как если бы фоновый поток спал.

Однако, если вы продолжаете порождать фоновые потоки и все время оставляете их заблокированными на read(), у вас будет довольно серьезная утечка памяти в ваших руках.Это не приведет к снижению производительности с точки зрения скорости или чего-либо подобного, но в конечном итоге приведет к падению вашего приложения.

Так что да, важно убедиться, что ваши фоновые потоки в конечном итоге завершатся (или, по крайней мере, гарантировать, что ваш код не будет продолжать пытаться добавлять новые, если существующие не прекращаются).

Это должно решить оригинальную проблему:

public interface StreamDataHandler {
    public void handleData(byte[] buffer, int numBytes);
    public void readFailedWithError(Exception ex);
}

public class DataReader extends Thread {
    private StreamDataHandler handler;
    private InputStream input;

    public DataReader(InputStream in, StreamDataHandler handler) {
        super();
        this.input = in;
        this.handler = handler;
    }

    @Override
    public void run() {
        int numRead = 0;
        byte[] buffer = new byte[1024];
        try {
            while ((numRead = input.read(buffer)) != -1) {
                if (this.handler != null && numRead > 0) {
                    this.handler.handleData(buffer, numRead);
                }
            }
        }
        catch (Exception e) {
            if (this.handler != null) {
                this.handler.readFailedWithError(e);
            }
        }
    }
}
0 голосов
/ 24 февраля 2012

Вы можете попытаться использовать Runnable или AsyncTask, чтобы обойти любые проблемы блокировки потоков.

Runnable

AsyncTask

В качестве альтернативы вы можете посмотреть, почему выбрасывается это исключение.Вы можете перехватить исключение, а затем повторно вызывать функцию TimerTask «available ()», пока она не будет выполнена успешно.

TimerTask

...