Почему больше Java не кодирует, используют PipedInputStream / PipedOutputStream?

Объявите переменную вне области действия функции, затем просто измените ее в функции:

let success = '';

docClient.query(params, function(err, data) {
    if (err) {
        console.error("Unable to read item. Error JSON:", JSON.stringify(err,
        null, 2));
    } else {
        console.log("GetItem succeeded:", JSON.stringify(data, null, 2));
        success = data.Items[0].hash_key;
    }
});
48
задан Machavity 9 December 2018 в 07:36
поделиться

6 ответов

От Javadocs:

Как правило, данные считаны с объекта PipedInputStream одним потоком, и данные записаны в соответствующий PipedOutputStream некоторым другим потоком. Попытка использовать оба объекта от единственного потока не рекомендуется, поскольку она может завести в тупик поток.

Это может частично объяснить, почему это не является более наиболее часто используемым.

я предположил бы, что другая причина состоит в том, что многие разработчики не понимают ее цели / преимущество.

45
ответ дан Mike Morearty 7 November 2019 в 12:38
поделиться

В Вашем примере Вы создаете два потока, чтобы сделать работу, которая могла быть сделана одним. И введение ввода-вывода задерживается в соединение.

у Вас есть лучший пример? Или я просто отвечал на Ваш вопрос.

<час>

Для получения по запросу некоторых комментариев (по крайней мере, мое представление их) в основной ответ:

  • Параллелизм вводит сложность в приложение. Вместо того, чтобы иметь дело с единственным линейным потоком данных, Вы теперь должны быть обеспокоены упорядочиванием независимых потоков данных. В некоторых случаях добавленная сложность может быть выровнена по ширине, особенно если можно усилить несколько ядер/Центральных процессоров, чтобы сделать интенсивную ЦП работу.
  • , Если Вы находитесь в ситуации, где можно извлечь выгоду из параллельных операций, обычно существует лучший способ скоординировать поток данных между потоками. Например, передавая объекты между потоками с помощью параллельной очереди, вместо того, чтобы перенести переданные по каналу потоки в объектные потоки.
  • то, Где переданный по каналу поток может быть хорошим решением, - когда у Вас есть несколько потоков, выполняющих обработку текста, а-ля конвейер Unix (например: grep | вид).
<час>

В определенном примере, переданный по каналу поток позволяет использование существующего класса реализации RequestEntity, обеспеченного HttpClient. Я полагаю, что лучшее решение состоит в том, чтобы создать новый класс реализации, как ниже, потому что примером является в конечном счете последовательная операция, которая не может извлечь выгоду из сложности и наверху параллельной реализации. В то время как я показываю RequestEntity анонимным классом, возможность многократного использования указала бы, что это должен быть первоклассный класс.

post.setRequestEntity(new RequestEntity()
{
    public long getContentLength()
    {
        return 0-1;
    }

    public String getContentType()
    {
        return "text/xml";
    }

    public boolean isRepeatable()
    {
        return false;
    }

    public void writeRequest(OutputStream out) throws IOException
    {
        output.setByteStream(out);
        serializer.write(doc, output);
    }
});
7
ответ дан kdgregory 7 November 2019 в 12:38
поделиться

Я слишком только недавно обнаружил классы PipedInputStream/PipedOutputStream.

я разрабатываю плагин Eclipse, который должен выполнить команды на удаленном сервере через SSH. Я использую JSch и Канал чтения API от входного потока и записей к потоку вывода. Но я должен подать команды через входной поток и считать ответы из потока вывода. Это - то, где PipedInput/OutputStream входит.

import java.io.PipedInputStream;
import java.io.PipedOutputStream;

import com.jcraft.jsch.Channel;

Channel channel;
PipedInputStream channelInputStream = new PipedInputStream();
PipedOutputStream channelOutputStream = new PipedOutputStream();

channel.setInputStream(new PipedInputStream(this.channelOutputStream));
channel.setOutputStream(new PipedOutputStream(this.channelInputStream));
channel.connect();

// Write to channelInputStream
// Read from channelInputStream

channel.disconnect();
6
ответ дан Brian Matthews 7 November 2019 в 12:38
поделиться

Кроме того, назад к исходному примеру: нет, это точно не минимизирует использование памяти также. Дерево (деревья) DOM получает созданную, сделанную буферизацию в оперативной памяти - в то время как это лучше, чем полные копии массива байтов, дело не в этом намного лучше. Но буферизация в этом случае будет медленнее; и дополнительный поток также создается - Вы не можете использовать пару PipedInput/OutputStream из единственного потока.

Иногда PipedXxxStreams полезны, но причина, они не используются больше, состоит в том, потому что довольно часто они не правильное решение. Они хорошо для коммуникации межпотока, и это - то, где я использовал их для того, что это стоит. Это просто, что нет то, что много вариантов использования для этого, учитывая то, как SOA раздвигает большинство таких границ быть между сервисами, вместо между потоками.

4
ответ дан StaxMan 7 November 2019 в 12:38
поделиться

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

я мог бы взглянуть на их исходный код andsee, если я вижу, какова проблема, возможно, была.

2
ответ дан Adrian Pronk 7 November 2019 в 12:38
поделиться

Так, что случилось с этой идиомой? Если нет ничего неправильно с этой идиомой, почему я не видел его?

РЕДАКТИРОВАНИЕ: для разъяснения PipedInputStream и PipedOutputStream заменяют шаблонную копию буфера буфером, которая обнаруживается везде, и они также позволяют Вам обрабатывать входящие данные одновременно с выписыванием обработанных данных. Они не используют каналы ОС.

Вы заявили, что это делает, но не указало, почему Вы делаете это.

, Если Вы полагаете, что это или уменьшит ресурсы, используемые (CPU/память), или улучшит производительность затем, это не сделает также. Однако это сделает Ваш код более сложным.

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

0
ответ дан Peter Lawrey 7 November 2019 в 12:38
поделиться
Другие вопросы по тегам:

Похожие вопросы: