JavaRush /จาวาบล็อก /Random-TH /กระแสที่ไม่ธรรมดา
Oleg Savenko
ระดับ
Одесса

กระแสที่ไม่ธรรมดา

เผยแพร่ในกลุ่ม
ด้วย Java เวอร์ชันใหม่แต่ละเวอร์ชันจะมีความสมบูรณ์ยิ่งขึ้น แม้ว่าความสมบูรณ์จะอยู่ในเวอร์ชันก่อนๆ แต่ภาษาก็มีการปรับปรุงอย่างต่อเนื่องทั้งในด้านระเบียบวิธีและการนำไปปฏิบัติ คอลเลกชันใน Java ก็ไม่มีข้อยกเว้น กรอบงานคอลเลกชันหลักปรากฏใน J2SE 1.2 และได้รับการพัฒนาอย่างต่อเนื่อง โดยผ่านการเปลี่ยนแปลงที่น่าพึงพอใจมากกว่าน่าผิดหวัง ด้วยการเปิดตัว JDK 5 คอลเลกชันมีความสะดวก รวดเร็ว และง่ายต่อการทำงานมากขึ้น สิ่งนี้นำไปสู่ความจริงที่ว่าโปรแกรมเมอร์เริ่มใช้ประโยชน์จากพวกมันอย่างเข้มข้นมากขึ้น รูปแบบบางอย่างได้รับการพัฒนาสำหรับการทำงานร่วมกับสิ่งเหล่านี้ ซึ่งไม่ต้องสงสัยเลยว่ามีประสิทธิภาพ แต่ด้วย JDK 8 คอลเลกชันก็ดีขึ้นอีกครั้ง และดีขึ้นด้วยเธรด เห็นได้ชัดว่าเนื่องจากคอลเลกชันสามารถแสดงในรูปแบบของสตรีมวิธีการทำงานร่วมกับคอลเลกชันเหล่านั้นก็จะเปลี่ยนไปเช่นกัน ดังนั้น ฉันต้องการแสดงให้เห็นว่าโซลูชันที่คุ้นเคยและเข้าใจง่ายสำหรับคอลเลกชันนั้นง่ายยิ่งขึ้นเพียงใด

ตัวอย่างที่ 1 ไม่มีอะไรจะง่ายกว่านี้อีกแล้ว

แน่นอนว่ามาเริ่มกันที่สิ่งที่ง่ายที่สุด มาดูองค์ประกอบทั้งหมดของคอลเลกชันและแสดงองค์ประกอบทั้งหมดกัน
// создадим и заполним список
   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);
อย่างที่คุณสังเกตเห็น มีไวยากรณ์ใหม่ที่ในความคิดของฉันในฐานะมือใหม่ Java นั้นง่ายกว่ามาก ดังนั้นสิ่งที่มองเห็นได้ในไวยากรณ์ใหม่:
берем_список(list).превращаем_в_поток(stream).перебираем_все_элементы(forEach)(тут_интуитивно_понятно)
System.out::println— ลิงก์ไปยังวิธีการแบบสแตติกที่ส่งออกสตริงไปยังคอนโซล แทนที่จะลิงก์ไปยังวิธีการแบบคงที่ คุณสามารถใช้รายการที่แตกต่างออกไปเล็กน้อยและไม่ชัดเจน:
list.stream().forEach(i -> System.out.println(i));
รายการนี้ใช้นิพจน์แลมบ์ดา ใช่แล้ว หากต้องการเรียนรู้วิธีทำงานกับสตรีม คุณจะต้องเรียนรู้สำนวนแลมบ์ดา ซึ่งมันวิเศษมาก นอกจากนี้ ฉันจะไม่แสดงวิธีการทำงานกับคอลเลกชันโดยใช้สตรีมเพียงอย่างเดียว โดยอาศัยข้อเท็จจริงที่ว่าคุณคุ้นเคยกับวิธีการแบบเดิมในระหว่างหลักสูตร

ตัวอย่างที่ 2 ค้นหาค่าคู่ในรายการและแสดงในคอนโซล

list.stream().filter(i -> i%2==0).forEach(System.out::println);
ปัญหาทั้งหมดได้รับการแก้ไขในบรรทัดเดียว ฉันหวังว่าคุณจะสนุกกับการทำงานในสายเดียว โดยใช้วิธีการนี้filterเราได้กรองสตรีมและส่งออกสิ่งที่เหลืออยู่ในคอนโซล ตัวกรองเป็นสิ่งที่ทรงพลังมากซึ่งสามารถช่วยได้ในกรณีที่ไม่คาดคิดที่สุด มาสร้างสรรค์และเปลี่ยนแปลงเงื่อนไขของปัญหากันเถอะ ตัวอย่างเช่น เราต้องนับจำนวนเลขคู่ในรายการ:
long count = list.stream().filter(i -> i%2==0).count();
และอีกครั้งในบรรทัดเดียว บางอย่างก็ดูเรียบง่ายไปหมด ในตัวกรอง เราใช้นิพจน์แลมบ์ดา ดังนั้นจึงวางเฉพาะตัวเลขคู่ในสตรีมใหม่ จากนั้นนำไปใช้กับสตรีมใหม่countซึ่งนับจำนวนองค์ประกอบที่อยู่ในสตรีมใหม่

ตัวอย่างที่ 3 ลองนับจำนวนคำในรายการที่มีความยาว 5 ตัวอักษร

เราเล่นกับจำนวนเต็มแล้ว ทีนี้มาเล่นกับคำศัพท์กันดีกว่า
List<String> list = new ArrayList<>();
Collections.addAll(list, "разые", "слова", "интересные", "And", "Not", "Very");

System.out.println(list.stream().filter(w -> w.length() == 5).count());
เราใช้ตัวกรองอีกครั้ง ในตัวกรอง โดยใช้นิพจน์แลมบ์ดา สตรีมใหม่จะแสดงขึ้น จากนั้นcountฉันก็คำนวณว่าสตรีมใหม่มีองค์ประกอบกี่องค์ประกอบ

ตัวอย่างที่ 4 พิมพ์คำที่ไม่ซ้ำ

งานที่คุ้นเคยเมื่อเราอ่านคำต่างๆ มากมายลงในคอลเลกชันจากไฟล์ และตอนนี้เราต้องการเพียงคำที่ไม่ซ้ำใครเท่านั้น
List<String> list = new ArrayList<>();
Collections.addAll(list, "Vasya", "Таня", "Olya", "Vasya", "Olya", "Сергей");

list.stream().distinct().forEach(System.out::println);
การดำเนินการหลักเสร็จสิ้นบนสตรีมโดยใช้distinct. ต่อไป ฉันขอแนะนำให้ดูงานบางอย่างของเราจากหลักสูตรโดยใช้ชุดข้อความ

ตัวอย่างที่ 5 คำยาว

ที่ระดับ 9 ของ Java Core ในการบรรยายที่ 11 มีปัญหาที่น่าสนใจในนั้นคุณต้องเขียนคำโดยคั่นด้วยเครื่องหมายจุลภาคใน File2 ซึ่งมีความยาวมากกว่า 6 อย่างเคร่งครัด ไม่ว่าคุณจะฟันดาบสวนประเภทใด ฉันเสนอวิธีแก้ปัญหาต่อไปนี้:
  1. จากไฟล์ต้นฉบับ เราจะอ่านคำทั้งหมดในรายการ

  2. จากนั้นเราดำเนินการบรรทัดต่อไปนี้

    Optional<String> rezult = list.stream()
    				.filter(w->w.length()>6)
    				.reduce((w1,w2)->w1+", "+w2);
  3. result.get()เขียนลงไฟล์

นี่เป็นวิธีแก้ปัญหาที่น่าสนใจโดยใช้เธรด ตัวกรองถูกกรอง และใช้การย่อและนิพจน์ทั่วไป สตริงที่จำเป็นจึงถูกสร้างขึ้น

ตัวอย่างที่ 6 คำที่มีตัวเลข

เขียนคำทั้งหมดที่มีตัวเลข เช่น a1 หรือ abc3d โดยคั่นด้วยช่องว่างใน File2 นี่เป็นเงื่อนไขจากหนังสือปัญหาของเราเช่นกัน ดังที่คุณเดาไว้ วิธีแก้ปัญหานั้นง่ายมาก
Optional<String> rezult = list.stream()
				.filter(w->w.matches(".*?\\d+.*?"))
				.reduce((w1,w2)->w1+" "+w2);
เรากรองสตรีมโดยใช้นิพจน์ทั่วไป จากนั้นลดนิพจน์แลมบ์ดา เหมือนกับงานก่อนหน้านี้มาก

ตัวอย่างที่ 7 การเลือกหมายเลข

งานทั้งหมดมีลักษณะดังนี้:
  • อ่าน 2 ชื่อไฟล์จากคอนโซล
  • ส่งออกตัวเลขทั้งหมดที่อยู่ในไฟล์แรกไปยังไฟล์ที่สอง
  • ตัวเลขจะถูกคั่นด้วยช่องว่าง
  • ปิดสตรีม.
สำหรับงานหลักคือการเขียนตัวเลขลงในสตริงโดยคั่นด้วยช่องว่างหากต้องการเขียนไฟล์เพิ่มเติมผมขอแนะนำให้ใช้สตรีมจะมีลักษณะดังนี้:
Optional<String> rezult = list.stream().filter(w->w.matches("\\d+"))
				.reduce((w1,w2)->w1+" "+w2);
System.out.println(rezult.get());
การใช้เธรดทำให้ปัญหาได้รับการแก้ไขด้วยวิธีที่ง่ายมาก แต่ดูเถิด เปรียบเทียบวิธีแก้ปัญหานี้กับสองวิธีก่อนหน้านี้ด้วยตัวคุณเอง สรุปบทความฉันต้องการสารภาพกับคุณ: พวกคุณฉันโกงเมื่อเลือกตัวอย่าง ความจริงก็คือฉันเลือกตัวอย่างที่ง่ายที่สุดเพื่อแสดงหัวข้อที่ไม่คุ้นเคยโดยใช้ปัญหาที่คุ้นเคย แน่นอนว่าเธรดนั้นใช้สำหรับทั้งงานที่เรียบง่ายและซับซ้อนมากขึ้น แต่ดังที่ Horstman เน้นย้ำในหนังสือของเขา “กระแสข้อมูลดำเนินการบนหลักการของ “อะไร ไม่ใช่อย่างไร” ซึ่งหมายความว่างานที่ซับซ้อนก่อนหน้านี้หลายอย่างจะง่ายขึ้น ฉันไม่รู้เกี่ยวกับคุณ แต่ฉันชอบกระแส ฉันหวังว่าฉันจะไม่กีดกันคุณจากการเรียนรู้สิ่งเหล่านั้น และให้ฉันอธิบายอีกเรื่องหนึ่ง:
  1. ฉันไม่ได้ตั้งใจที่จะสอนผู้อ่านถึงวิธีใช้สตรีมในคอลเลกชัน ฉันไม่ใช่ครูที่มีประสบการณ์ขนาดนั้น ฉันอยากจะแสดงให้คุณเห็นว่ากระทู้นั้นเรียบง่ายและน่าสนใจมาก! โดยทั่วไปนี่เป็นสิ่งจำเป็น
  2. ยิ่งฉันเข้าใจกระแสมากเท่าไร ฉันก็ยิ่งมองเห็นปัญหาที่พวกเขาแก้ไขปัญหาทั้งหมดจากหนังสือเรียนมากขึ้นเท่านั้น ซึ่งหมายความว่ากระแสนั้นไม่ได้ถูกประดิษฐ์ขึ้นโดยเปล่าประโยชน์
  3. สตรีมไม่เพียงแต่ใช้งานง่ายเท่านั้น แต่ยังมีข้อได้เปรียบที่สำคัญอีกด้วย เมื่อทำงานกับข้อมูลจำนวนมาก สตรีมมักจะมีประสิทธิภาพมากกว่า
ปล . ฉันล้อเล่นเกี่ยวกับปัญหาทั้งหมด แนะนำ:ไลบรารี Java ระดับมืออาชีพ เล่มที่ 2 เครื่องมือการเขียนโปรแกรมขั้นสูง เคย์ ฮอร์สต์มันน์. ฉันมีฉบับที่สิบ
ความคิดเห็น
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION