Ответ
Stream API в Java работает с данными из различных источников:
- Коллекции: Любые классы, реализующие интерфейс
Collection(List,Set,Queue).List<String> list = Arrays.asList("a", "b", "c"); Stream<String> streamFromList = list.stream(); - Массивы: Через утилитарный класс
Arrays.String[] array = {"a", "b", "c"}; Stream<String> streamFromArray = Arrays.stream(array); - Примитивные потоки: Специализированные интерфейсы
IntStream,LongStream,DoubleStream.IntStream intStream = IntStream.range(1, 5); // 1, 2, 3, 4 - Файлы: Через методы класса
Files.Stream<String> lines = Files.lines(Paths.get("file.txt")); - Генераторы и итераторы: Методы
Stream.generate(),Stream.iterate().Stream<Double> randomStream = Stream.generate(Math::random).limit(5); - Другие источники: Любые объекты, реализующие интерфейс
IterableилиIterator.
Важно: Stream не хранит данные и не изменяет исходную коллекцию. Операции делятся на промежуточные (lazy, например filter, map) и терминальные (eager, например collect, forEach), которые запускают выполнение конвейера.
Ответ 18+ 🔞
А, ну вот, Stream API в Java, да? Это ж как водопровод для данных, только вместо воды — объекты, а вместо сантехника — ты, с кривыми руками. Слушай, а источников-то у него, блядь, овердохуища! Прям как у меня в молодости вариантов, куда пойти нажраться.
Ну, во-первых, коллекции всякие. Любая шняга, что Collection реализует — List, Set, эта Queue ваша. Берёшь и просто stream() вызываешь, всё, понеслась душа в рай.
List<String> list = Arrays.asList("a", "b", "c");
Stream<String> streamFromList = list.stream();
Проще пареной репы, ёпта. Никаких тебе ритуалов с бубном.
Массивы — тоже не проблема. Тут тебе Arrays.stream() в помощь, как добрый самаритянин.
String[] array = {"a", "b", "c"};
Stream<String> streamFromArray = Arrays.stream(array);
А вот для примитивов — отдельная песня, блядь. Чтобы не ебаться с автоупаковкой туда-сюда, сделали специальные штуки: IntStream, LongStream, DoubleStream. Красота!
IntStream intStream = IntStream.range(1, 5); // 1, 2, 3, 4
Чисто, аккуратно, без лишнего геморроя.
Файлы тоже можно в стрим превратить, представляешь? Files.lines() — и вот тебе поток строк, читай, не хочу.
Stream<String> lines = Files.lines(Paths.get("file.txt"));
Главное, потом не забудь закрыть, а то ресурсы похудеют.
Ещё есть генераторы с итераторами, это вообще магия, блядь. Хочешь бесконечный поток случайных чисел? Пожалуйста!
Stream<Double> randomStream = Stream.generate(Math::random).limit(5);
limit(5) — это чтобы не улететь в космос, а то комп загорится, хитрая жопа.
Ну и вообще, любую хуйню, что Iterable или Iterator реализует, можно в стрим запихнуть. Универсальная хрень, в общем.
А теперь, внимание, ебаный рот! Запомни раз и нахуй: Stream — это не хранилище. Он данные не держит и исходную коллекцию не портит. Всё работает по принципу конвейера.
Есть промежуточные операции (типа filter, map) — они ленивые, сука. Пока ты не скажешь "давай, блядь, результат", они нихуя не делают, просто план строят.
А есть терминальные (collect, forEach) — вот это жадные твари. Как только их вызываешь, весь этот построенный план начинает выполняться, и конвейер выдаёт тебе что-то осязаемое. Или просто делает дело и молча сходит со сцены.
Вот и вся философия. Не усложняй, просто бери и делай.