วิธีการทำงานกับกลุ่มที่ถูกจับ
ซอร์สโค้ดของแอปพลิเค ชันมี การRegexDemo
เรียกเมธอด m.group()
วิธีนี้group()
เป็นหนึ่งในหลายวิธีของชั้นเรียนMatcher
ที่มุ่งทำงานกับกลุ่มที่ถูกจับ:
-
วิธีการ
int groupCount()
ส่งกลับจำนวนของกลุ่มที่บันทึกในรูปแบบตัวแก้ไข หมายเลขนี้ไม่ได้คำนึงถึงกลุ่มการจับพิเศษหมายเลข 0 ซึ่งสอดคล้องกับรูปแบบโดยรวม -
วิธีการ
String group()
ส่งกลับอักขระของการจับคู่ก่อนหน้าที่พบ หากต้องการรายงานการค้นหาสตริงว่างที่สำเร็จ เมธอดนี้จะส่งคืนสตริงว่าง หากตัวแก้ไขยังไม่ได้ดำเนินการค้นหาหรือการดำเนินการค้นหาก่อนหน้านี้ล้มเหลว ข้อยกเว้นจะถูกส่งออกIllegalStateException
ไป -
วิธีการนี้
String group(int group)
คล้ายกับวิธีก่อนหน้า ยกเว้นว่าจะส่งคืนอักขระของรายการที่ตรงกันก่อนหน้านี้ ซึ่งบันทึกโดยหมายเลขกลุ่มที่ระบุโดยgroup
พารามิเตอร์ โปรดทราบว่านี่group(0)
เทียบเท่าgroup()
กับ หากเทมเพลตไม่มีกลุ่มที่บันทึกไว้ตามหมายเลขที่กำหนด วิธีการจะส่งข้อIndexOutOfBoundsException
ยกเว้น หากตัวแก้ไขยังไม่ได้ดำเนินการค้นหาหรือการดำเนินการค้นหาก่อนหน้านี้ล้มเหลว ข้อยกเว้นจะถูกส่งออกIllegalStateException
ไป -
วิธีการ
String group(String name)
ส่งกลับอักขระของการจับคู่ก่อนหน้าที่พบซึ่งบันทึกโดยกลุ่มชื่อ หากชื่อกลุ่มที่บันทึกไม่อยู่ในเทมเพลต ข้อยกเว้นจะถูกส่งออกIllegalArgumentException
ไป หากตัวแก้ไขยังไม่ได้ดำเนินการค้นหาหรือการดำเนินการค้นหาก่อนหน้านี้ล้มเหลว ข้อยกเว้นจะถูกส่งออกIllegalStateException
ไป
groupCount()
และ วิธีการ group(int group)
:
Pattern p = Pattern.compile("(.(.(.)))");
Matcher m = p.matcher("abc");
m.find();
System.out.println(m.groupCount());
for (int i = 0; i <= m.groupCount(); i++)
System.out.println(i + ": " + m.group(i));
ผลการดำเนินการ:
3
0: abc
1: abc
2: bc
3: c

วิธีการกำหนดตำแหน่งการแข่งขัน
คลาสนี้Matcher
มีหลายวิธีที่จะส่งคืนตำแหน่งเริ่มต้นและจุดสิ้นสุดของการแข่งขัน:
-
วิธีการ
int start()
ส่งกลับตำแหน่งเริ่มต้นของการแข่งขันครั้งก่อนที่พบ หากตัวแก้ไขยังไม่ได้ดำเนินการค้นหาหรือการดำเนินการค้นหาก่อนหน้านี้ล้มเหลว ข้อยกเว้นจะถูกส่งออกIllegalStateException
ไป -
วิธีการนี้คล้าย
int start(int group)
กับวิธีก่อนหน้า แต่จะส่งคืนตำแหน่งเริ่มต้นของรายการที่ตรงกันก่อนหน้านี้ซึ่งพบสำหรับกลุ่มที่มีการระบุหมายเลขโดยพารามิเตอร์group
หากเทมเพลตไม่มีกลุ่มที่บันทึกไว้ตามหมายเลขที่กำหนด วิธีการจะส่งข้อIndexOutOfBoundsException
ยกเว้น หากตัวแก้ไขยังไม่ได้ดำเนินการค้นหาหรือการดำเนินการค้นหาก่อนหน้านี้ล้มเหลว ข้อยกเว้นจะถูกส่งออกIllegalStateException
ไป -
วิธีการนี้
int start(String name)
คล้ายกับวิธีก่อนหน้า แต่จะส่งคืนตำแหน่งเริ่มต้นของรายการที่ตรงกันก่อนหน้าซึ่งพบสำหรับกลุ่มที่เรียกname
ว่า หากกลุ่มที่บันทึกname
ไม่อยู่ในเทมเพลต จะมีข้อยกเว้นเกิดIllegalArgumentException
ขึ้น หากตัวแก้ไขยังไม่ได้ดำเนินการค้นหาหรือการดำเนินการค้นหาก่อนหน้านี้ล้มเหลว ข้อยกเว้นจะถูกส่งออกIllegalStateException
ไป -
เมธอด
int end()
ส่งคืนตำแหน่งของอักขระตัวสุดท้ายของการจับคู่ก่อนหน้าที่พบบวก 1 หากตัวจับคู่ยังไม่ได้ดำเนินการจับคู่หรือการดำเนินการค้นหาก่อนหน้านี้ล้มเหลว ข้อยกเว้นจะถูกส่งออกIllegalStateException
ไป -
วิธีการนี้คล้าย
int end(int group)
กับวิธีก่อนหน้า แต่จะส่งคืนตำแหน่งสิ้นสุดของการจับคู่ก่อนหน้าซึ่งพบสำหรับกลุ่มที่มีการระบุหมายเลขโดยพารามิเตอร์group
หากเทมเพลตไม่มีกลุ่มที่บันทึกไว้ตามหมายเลขที่กำหนด วิธีการจะส่งข้อIndexOutOfBoundsException
ยกเว้น หากตัวแก้ไขยังไม่ได้ดำเนินการค้นหาหรือการดำเนินการค้นหาก่อนหน้านี้ล้มเหลว ข้อยกเว้นจะถูกส่งออกIllegalStateException
ไป -
วิธีการนี้
int end(String name)
คล้ายกับวิธีก่อนหน้า แต่จะส่งคืนตำแหน่งสิ้นสุดของรายการที่ตรงกันก่อนหน้าซึ่งพบสำหรับกลุ่มที่เรียกname
ว่า หากกลุ่มที่บันทึกname
ไม่อยู่ในเทมเพลต จะมีข้อยกเว้นเกิดIllegalArgumentException
ขึ้น หากตัวแก้ไขยังไม่ได้ดำเนินการค้นหาหรือการดำเนินการค้นหาก่อนหน้านี้ล้มเหลว ข้อยกเว้นจะถูกส่งออกIllegalStateException
ไป
Pattern p = Pattern.compile("(.(.(.)))");
Matcher m = p.matcher("abcabcabc");
while (m.find())
{
System.out.println("Найдено " + m.group(2));
System.out.println(" начинается с позиции " + m.start(2) +
" и заканчивается на позиции " + (m.end(2) - 1));
System.out.println();
}
ผลลัพธ์ของตัวอย่างนี้มีดังต่อไปนี้:
Найдено bc
начинается с позиции 1 и заканчивается на позиции 2
Найдено bc
начинается с позиции 4 и заканчивается на позиции 5
Найдено bc
начинается с позиции 7 и заканчивается на позиции 8
วิธีการของคลาส PatternSyntaxException
อินสแตนซ์ของคลาสPatternSyntaxException
อธิบายข้อผิดพลาดทางไวยากรณ์ในนิพจน์ทั่วไป โยนข้อยกเว้นดังกล่าวจากวิธีการcompile()
และmatches()
คลาสPattern
และถูกสร้างขึ้นผ่านตัวสร้างต่อไปนี้: PatternSyntaxException(String desc, String regex, int index)
ตัวสร้างนี้เก็บคำอธิบายที่ระบุ ( desc
) นิพจน์ทั่วไป ( regex
) และตำแหน่งที่เกิดข้อผิดพลาดทางไวยากรณ์ หากไม่ทราบตำแหน่งของข้อผิดพลาดทางไวยากรณ์ ค่าindex
จะถูกตั้ง ค่า -1
เป็น เป็นไปได้มากว่าคุณไม่จำเป็นต้องสร้างอินสแตนซ์ของไฟล์PatternSyntaxException
. อย่างไรก็ตาม คุณจะต้องแยกค่าข้างต้นเมื่อสร้างข้อความแสดงข้อผิดพลาดที่จัดรูปแบบ เมื่อต้องการทำเช่นนี้ คุณสามารถใช้วิธีการต่อไปนี้:
- วิธีการ
String getDescription()
ส่งกลับคำอธิบายของข้อผิดพลาดทางไวยากรณ์ - วิธีการ
int getIndex()
ส่งคืนตำแหน่งที่เกิดข้อผิดพลาด หรือ -1 หากไม่ทราบตำแหน่ง - วิธีการ
String getPattern()
ส่งกลับนิพจน์ทั่วไปที่ไม่ถูกต้อง
String getMessage()
จะส่งคืนสตริงหลายบรรทัดด้วยค่าที่ส่งคืนจากวิธีก่อนหน้า พร้อมด้วยการแสดงภาพว่าเกิดข้อผิดพลาดทางไวยากรณ์ที่ใดในเทมเพลต ข้อผิดพลาดทางไวยากรณ์คืออะไร? ตัวอย่าง: java RegexDemo (?itree Treehouse
ในกรณีนี้ เราลืมระบุเมตาอักขระวงเล็บปิด ( )
) ในนิพจน์แฟล็กที่ซ้อนกัน นี่คือผลลัพธ์จากข้อผิดพลาดนี้:
regex = (?itree
input = Treehouse
Неправильное регулярное выражение: Unknown inline modifier near index 3
(?itree
^
Описание: Unknown inline modifier
Позиция: 3
Неправильный шаблон: (?itree
สร้างแอปพลิเคชันนิพจน์ทั่วไปที่มีประโยชน์โดยใช้ Regex API
นิพจน์ทั่วไปช่วยให้คุณสร้างแอปพลิเคชันการประมวลผลข้อความที่มีประสิทธิภาพได้ ในส่วนนี้ เราจะแสดงแอปพลิเคชันที่มีประโยชน์สองแอปพลิเคชันให้คุณดู ซึ่งหวังว่าจะสนับสนุนให้คุณสำรวจคลาสและวิธีการของ Regex API เพิ่มเติม ภาคผนวกที่สองแนะนำ Lexan: ไลบรารีโค้ดที่นำมาใช้ซ้ำได้สำหรับการวิเคราะห์คำศัพท์
นิพจน์ทั่วไปและเอกสารประกอบ
เอกสารประกอบเป็นหนึ่งในงานบังคับในการพัฒนาซอฟต์แวร์ระดับมืออาชีพ โชคดีที่นิพจน์ทั่วไปสามารถช่วยคุณในการสร้างเอกสารได้หลายด้าน รหัสในรายการ 1 แยกบรรทัดที่มีความคิดเห็นสไตล์ C บรรทัดเดียวและหลายบรรทัดจากไฟล์ต้นฉบับและเขียนลงในไฟล์อื่น เพื่อให้โค้ดใช้งานได้ ความคิดเห็นจะต้องอยู่ในบรรทัดเดียวกัน รายการ 1. การดึงความคิดเห็นimport java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.regex.PatternSyntaxException;
public class ExtCmnt
{
public static void main(String[] args)
{
if (args.length != 2)
{
System.err.println("Способ применения: java ExtCmnt infile outfile");
return;
}
Pattern p;
try
{
// Следующий шаблон определяет многострочные комментарии,
// располагающиеся в одной строке (например, /* одна строка */)
// и однострочные комментарии (например, // Howая-то строка).
// Комментарий может располагаться в любом месте строки.
p = Pattern.compile(".*/\\*.*\\*/|.*//.*$");
}
catch (PatternSyntaxException pse)
{
System.err.printf("Синтаксическая ошибка в регулярном выражении: %s%n", pse.getMessage());
System.err.printf("Описание ошибки: %s%n", pse.getDescription());
System.err.printf("Позиция ошибки: %s%n", pse.getIndex());
System.err.printf("Ошибочный шаблон: %s%n", pse.getPattern());
return;
}
try (FileReader fr = new FileReader(args[0]);
BufferedReader br = new BufferedReader(fr);
FileWriter fw = new FileWriter(args[1]);
BufferedWriter bw = new BufferedWriter(fw))
{
Matcher m = p.matcher("");
String line;
while ((line = br.readLine()) != null)
{
m.reset(line);
if (m.matches()) /* Должна соответствовать вся строка */
{
bw.write(line);
bw.newLine();
}
}
}
catch (IOException ioe)
{
System.err.println(ioe.getMessage());
return;
}
}
}
วิธีการmain()
ในรายการ 1 จะตรวจสอบไวยากรณ์บรรทัดคำสั่งที่ถูกต้องก่อน จากนั้นจึงรวบรวมนิพจน์ทั่วไปที่ออกแบบมาเพื่อตรวจจับความคิดเห็นบรรทัดเดียวและหลายบรรทัดในอ็อบเจ็กต์Pattern
คลาส หากไม่มีข้อยกเว้นPatternSyntaxException
วิธีการmain()
จะเปิดไฟล์ต้นฉบับ สร้างไฟล์เป้าหมาย รับตัวจับคู่เพื่อจับคู่แต่ละบรรทัดที่อ่านกับรูปแบบ จากนั้นอ่านไฟล์ต้นฉบับทีละบรรทัด สำหรับแต่ละบรรทัด จะจับคู่กับรูปแบบความคิดเห็น หากสำเร็จ วิธีการนี้main()
จะเขียนสตริง (ตามด้วยการขึ้นบรรทัดใหม่) ไปยังไฟล์เป้าหมาย (เราจะครอบคลุมตรรกะ I/O ของไฟล์ในบทช่วยสอน Java 101 ในอนาคต) คอมไพล์รายการ 1 ดังนี้: javac ExtCmnt.java
เรียกใช้แอปพลิเคชันด้วยไฟล์ExtCmnt.java
เป็นอินพุต: java ExtCmnt ExtCmnt.java out
คุณควรได้รับผลลัพธ์ต่อไปนี้ในไฟล์ออก:
// Следующий шаблон определяет многострочные комментарии,
// располагающиеся в одной строке (например, /* одна строка */)
// и однострочные комментарии (например, // Howая-то строка).
// Комментарий может располагаться в любом месте строки.
p = Pattern.compile(".*/\\*.*\\*/|.*//.*$");
if (m.matches()) /* Должна соответствовать вся строка */
ในสตริงรูปแบบ อักขระ.*/\\*.*\\*/|.*//.*$
เมตาไปป์|
ทำหน้าที่เป็นตัวดำเนินการเชิงตรรกะหรือ ซึ่งบ่งชี้ว่าตัวจับคู่ควรใช้ตัวถูกดำเนินการทางซ้ายของโครงสร้างนิพจน์ทั่วไปที่กำหนดเพื่อค้นหารายการที่ตรงกันในข้อความตัวจับคู่ หากไม่มีรายการที่ตรงกัน ตัวจับคู่จะใช้ตัวถูกดำเนินการที่ถูกต้องจากโครงสร้างนิพจน์ทั่วไปที่กำหนดสำหรับการพยายามค้นหาอีกครั้ง (อักขระเมตาวงเล็บในกลุ่มที่บันทึกไว้จะสร้างตัวดำเนินการเชิงตรรกะด้วย) นิพจน์ทั่วไปใน Java ตอนที่ 5
GO TO FULL VERSION