JavaRush /Blog Java /Random-MS /Aliran ringkas bukan ringkas
Oleg Savenko
Tahap
Одесса

Aliran ringkas bukan ringkas

Diterbitkan dalam kumpulan
Dengan setiap versi baharu Java ia menjadi lebih kaya dan lebih kaya. Walaupun kebanyakan kekayaan terletak pada versi terdahulu, bahasa itu terus bertambah baik dalam kedua-dua metodologi dan pelaksanaan. Koleksi di Jawa tidak terkecuali. Rangka kerja koleksi teras muncul dalam J2SE 1.2 dan terus berkembang, mengalami perubahan yang lebih menggembirakan daripada mengecewakan. Dengan keluaran JDK 5, koleksi telah menjadi lebih mudah, lebih pantas dan lebih mudah untuk digunakan. Ini membawa kepada fakta bahawa pengaturcara mula mengeksploitasi mereka dengan lebih intensif. Corak tertentu telah dibangunkan untuk bekerja dengan mereka, yang pastinya berkesan. Tetapi dengan JDK 8, koleksi menjadi lebih baik lagi dan menjadi lebih baik berkat urutan. Jelas sekali, disebabkan oleh fakta bahawa koleksi boleh diwakili dalam bentuk aliran, metodologi untuk bekerja dengan mereka juga akan berubah. Oleh itu, saya ingin menunjukkan bagaimana penyelesaian biasa dan mudah difahami dengan koleksi menjadi lebih mudah.

Contoh 1. Ia tidak boleh menjadi lebih mudah

Sudah tentu, mari kita mulakan dengan perkara yang paling mudah, mari kita pergi melalui semua elemen koleksi dan memaparkan semua elemen.
// создадим и заполним список
   List<Integer> list = new ArrayList<>();
   Collections.addAll(list, 1, 5, 6, 11, 3, 15, 7, 8);
   // а теперь
   // быстрый for по всем elementм, только для коллекций
   for (Integer i:list){
       System.out.println(i);
   }
   //но мы уже живем в JDK 8
   //а значит нужно так
   list.stream().forEach(System.out::println);
Seperti yang anda perhatikan, terdapat sintaks baharu yang, pada pendapat saya sebagai pemula Java, adalah lebih mudah. Jadi, apa yang boleh dilihat dalam sintaks baharu:
берем_список(list).превращаем_в_поток(stream).перебираем_все_элементы(forEach)(тут_интуитивно_понятно)
System.out::println— pautan ke kaedah statik yang mengeluarkan rentetan ke konsol Daripada pautan ke kaedah statik, anda boleh menggunakan masukan yang sedikit berbeza dan kurang jelas:
list.stream().forEach(i -> System.out.println(i));
Entri ini menggunakan ungkapan lambda. Dan ya, untuk belajar cara bekerja dengan strim, anda perlu mempelajari ungkapan lambda - ia sangat bagus. Selanjutnya, saya tidak akan menunjukkan cara bekerja dengan koleksi hanya menggunakan aliran, bergantung pada fakta bahawa anda menjadi biasa dengan kaedah tradisional semasa kursus.

Contoh 2. Cari nilai genap dalam senarai dan paparkannya dalam konsol

list.stream().filter(i -> i%2==0).forEach(System.out::println);
Keseluruhan masalah diselesaikan dalam satu baris. Saya harap anda seronok bekerja dalam satu barisan. Menggunakan kaedah itu, filterkami menapis aliran dan mengeluarkan apa yang tersisa kepada konsol. Penapis adalah perkara yang sangat berkuasa yang boleh membantu dalam kes yang paling tidak dijangka. Mari kreatif dan ubah keadaan masalah. Sebagai contoh, kita perlu mengira bilangan nombor genap dalam senarai:
long count = list.stream().filter(i -> i%2==0).count();
Dan sekali lagi dalam satu baris. Entah bagaimana semuanya kelihatan mudah. Dalam penapis, kami menggunakan ungkapan lambda, dengan itu hanya meletakkan nombor genap dalam strim baharu, dan kemudian digunakan pada strim baharu count, yang mengira bilangan elemen dalam strim baharu.

Contoh 3. Mari kita hitung berapa banyak perkataan dalam senarai yang mempunyai 5 aksara

Kami telah bermain dengan integer, sekarang mari bermain dengan perkataan.
List<String> list = new ArrayList<>();
Collections.addAll(list, "разые", "слова", "интересные", "And", "Not", "Very");

System.out.println(list.stream().filter(w -> w.length() == 5).count());
Kami menggunakan penapis semula. Dalam penapis, menggunakan ungkapan lambda, strim baharu dipaparkan, dan kemudian, difahami, countsaya mengira bilangan elemen dalam strim baharu.

Contoh 4. Cetak perkataan unik

Tugas biasa apabila kita membaca banyak perkataan yang berbeza ke dalam koleksi daripada fail, dan kini kita hanya memerlukan yang unik.
List<String> list = new ArrayList<>();
Collections.addAll(list, "Vasya", "Таня", "Olya", "Vasya", "Olya", "Сергей");

list.stream().distinct().forEach(System.out::println);
Tindakan utama telah dilakukan pada aliran menggunakan distinct. Seterusnya, saya cadangkan untuk melihat beberapa tugas kami dari kursus menggunakan benang

Contoh 5. Perkataan panjang

Pada tahap ke-9 Java Core, dalam kuliah 11 terdapat masalah yang menarik, di dalamnya anda perlu menulis perkataan yang dipisahkan dengan koma dalam File2, yang panjangnya lebih besar daripada 6. Tidak kira jenis taman yang anda pagar, Saya mencadangkan penyelesaian berikut:
  1. Dari fail sumber kami membaca semua perkataan ke dalam senarai.

  2. Kemudian kami melaksanakan baris berikut

    Optional<String> rezult = list.stream()
    				.filter(w->w.length()>6)
    				.reduce((w1,w2)->w1+", "+w2);
  3. result.get()tulis ke fail.

Berikut ialah penyelesaian yang menarik menggunakan benang. Penapis ditapis, dan menggunakan pengurangan dan ungkapan biasa, rentetan yang diperlukan telah dihasilkan.

Contoh 6. Perkataan dengan nombor

Tulis semua perkataan yang mengandungi nombor, contohnya, a1 atau abc3d, dipisahkan dengan ruang dalam File2. Ini juga merupakan syarat dari buku masalah kami, seperti yang anda rasa, penyelesaiannya mudah.
Optional<String> rezult = list.stream()
				.filter(w->w.matches(".*?\\d+.*?"))
				.reduce((w1,w2)->w1+" "+w2);
Kami menapis strim menggunakan ungkapan biasa, dan kemudian mengurangkan dan ungkapan lambda. Begitu banyak persamaan dengan tugasan sebelum ini.

Contoh 7. Memilih nombor

Seluruh tugas berbunyi seperti ini:
  • Baca 2 nama fail daripada konsol.
  • Output ke dalam fail kedua semua nombor yang ada dalam fail pertama.
  • Nombor dipisahkan oleh ruang.
  • Tutup strim.
Untuk tugas utama, iaitu menulis nombor ke dalam rentetan yang dipisahkan oleh ruang, untuk menulis selanjutnya ke fail, saya cadangkan menggunakan aliran, ia akan kelihatan seperti ini:
Optional<String> rezult = list.stream().filter(w->w.matches("\\d+"))
				.reduce((w1,w2)->w1+" "+w2);
System.out.println(rezult.get());
Menggunakan benang, masalah diselesaikan dengan cara yang sangat mudah. Tetapi, lihat dan lihat, bandingkan sendiri penyelesaian ini dengan dua penyelesaian sebelumnya. Menyimpulkan artikel itu, saya ingin mengaku kepada anda: kawan, saya menipu apabila saya memilih contoh. Hakikatnya ialah saya memilih contoh paling mudah untuk menunjukkan kepada anda topik yang tidak dikenali menggunakan masalah biasa. Sudah tentu, benang digunakan untuk kedua-dua tugas yang mudah dan lebih kompleks. Tetapi seperti yang ditekankan oleh Horstman dalam bukunya, "Aliran data beroperasi pada prinsip "apa, bukan bagaimana untuk dilakukan."," yang bermaksud banyak tugas yang rumit sebelum ini boleh menjadi lebih mudah. Saya tidak tahu tentang anda, tetapi saya suka alirannya, saya harap saya tidak menghalang anda daripada mempelajarinya. Dan izinkan saya menerangkan satu perkara lagi:
  1. Saya tidak berhasrat untuk mengajar pembaca cara menggunakan aliran dalam koleksi; Saya bukan seorang guru yang berpengalaman. Saya ingin menunjukkan kepada anda bahawa benang adalah mudah dan sangat menarik! Secara umum, ini adalah satu keperluan.
  2. Semakin saya memahami aliran, semakin saya melihat masalah di mana mereka menyelesaikan semua masalah dari buku kursus, yang bermaksud bahawa aliran tidak dicipta dengan sia-sia.
  3. Strim bukan sahaja mudah untuk digunakan, tetapi ia juga mempunyai kelebihan penting - apabila bekerja dengan jumlah data yang besar, strim selalunya lebih produktif.
PS . Saya bergurau tentang SEMUA MASALAH. Mengesyorkan: Pustaka Java profesional. Jilid 2 Alat pengaturcaraan lanjutan. Kay Horstmann. Saya mempunyai edisi kesepuluh.
Komen
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION