JavaRush /مدونة جافا /Random-AR /التعبيرات العادية في جافا، الجزء 2

التعبيرات العادية في جافا، الجزء 2

نشرت في المجموعة
نقدم انتباهكم إلى ترجمة دليل قصير للتعبيرات العادية في Java، كتبه Jeff Friesen لموقع javaworld . ولتسهيل القراءة قمنا بتقسيم المقال إلى عدة أجزاء. التعبيرات العادية في جافا، الجزء 2 - 1التعبيرات العادية في جافا، الجزء 1
دمج نطاقات متعددة
يمكنك دمج نطاقات متعددة في فئة أحرف نطاق واحدة عن طريق وضعها جنبًا إلى جنب. على سبيل المثال، يطابق الفصل [a-zA-Z]كافة الأحرف الأبجدية اللاتينية بأحرف صغيرة أو كبيرة.

دمج نطاقات متعددة

يمكنك دمج نطاقات متعددة في فئة أحرف نطاق واحدة عن طريق وضعها جنبًا إلى جنب. على سبيل المثال، يطابق الفصل [a-zA-Z]كافة الأحرف الأبجدية اللاتينية بأحرف صغيرة أو كبيرة.

الجمع بين فئات الشخصيات

يتكون اتحاد فئة الأحرف من عدة فئات أحرف متداخلة ويطابق جميع الأحرف في الاتحاد الناتج. على سبيل المثال، يطابق الفصل [a-d[m-p]]الأحرف من aإلى dومن mإلى p. خذ بعين الاعتبار المثال التالي: java RegexDemo [ab[c-e]] abcdef سيبحث هذا المثال عن الأحرف aو bو cو dو eالتي توجد تطابقات لها في abcdef:
regex = [ab[c-e]]
input = abcdef
Found [a] starting at 0 and ending at 0
Found [b] starting at 1 and ending at 1
Found [c] starting at 2 and ending at 2
Found [d] starting at 3 and ending at 3
Found [e] starting at 4 and ending at 4

تقاطع فئة الأحرف

يتكون تقاطع فئات الأحرف من أحرف مشتركة بين جميع الفئات المتداخلة ويطابق الأحرف المشتركة فقط. على سبيل المثال، يتطابق الفصل مع [a-z&&[d-f]]الأحرف و . خذ بعين الاعتبار المثال التالي: لاحظ أنه في نظام التشغيل Windows الخاص بي، تكون علامات الاقتباس المزدوجة مطلوبة لأن غلاف الأوامر يعاملها كفاصل أوامر. سيجد هذا المثال فقط الحرف الذي له تطابق في : defjava RegexDemo "[aeiouy&&[y]]" party&yparty
regex = [aeiouy&&[y]]
input = party
Found [y] starting at 4 and ending at 4

طرح فئات الأحرف

يتكون طرح فئات الأحرف من جميع الأحرف باستثناء تلك الموجودة في فئات الأحرف المتداخلة، ويطابق تلك الأحرف المتبقية فقط. على سبيل المثال، يطابق الفصل [a-z&&[^m-p]]الأحرف من aإلى lومن qإلى z: java RegexDemo "[a-f&&[^a-c]&&[^e]]" abcdefg سيبحث هذا المثال عن الأحرف dوالمطابقات fلها في abcdefg:
regex = [a-f&&[^a-c]&&[^e]]
input = abcdefg
Found [d] starting at 3 and ending at 3
Found [f] starting at 5 and ending at 5

فئات الأحرف المحددة مسبقًا

تظهر بعض فئات الأحرف بشكل متكرر بدرجة كافية في التعبيرات العادية لتبرير استخدام التدوين المختصر. يقدم الفصل Patternفئات أحرف محددة مسبقًا مثل هذه الاختصارات. يمكنك استخدامها لتبسيط التعبيرات العادية وتقليل الأخطاء النحوية. هناك عدة فئات من فئات الأحرف المحددة مسبقًا: الخصائص القياسية وPOSIX java.lang.CharacterوUnicode مثل البرنامج النصي والكتلة والفئة والثنائي. تعرض القائمة التالية فئة الفئات القياسية فقط:
  • \d: رقم. مقابل [0-9].
  • \D: حرف غير رقمي. مقابل [^0-9].
  • \s: حرف المسافة البيضاء. مقابل [ \t\n\x0B\f\r].
  • \S: ليس حرف مسافة بيضاء. مقابل [^\s].
  • \w: رمز تشكيل الكلمة. مقابل [a-zA-Z_0-9].
  • \W: ليست شخصية تشكيل الكلمات. مقابل [^\w].
يستخدم المثال التالي فئة أحرف محددة مسبقًا \wلوصف جميع أحرف الكلمات في النص المُدخل: java RegexDemo \w "aZ.8 _" انظر عن كثب إلى نتائج التنفيذ التالية، والتي توضح أن أحرف النقطة والمسافة لا تعتبر أحرفًا كلمة:
regex = \w
input = aZ.8 _
Found [a] starting at 0 and ending at 0
Found [Z] starting at 1 and ending at 1
Found [8] starting at 3 and ending at 3
Found [_] starting at 5 and ending at 5
فواصل الخط
تصف وثائق فئة SDK Patternالحرف التعريفي النقطي كفئة أحرف محددة مسبقًا تتطابق مع أي حرف باستثناء فواصل الأسطر (تسلسلات مكونة من حرف واحد أو حرفين تحدد نهاية السطر). الاستثناء هو الوضع dotall (الذي سنناقشه لاحقًا)، حيث تتطابق النقاط أيضًا مع فواصل الأسطر. يميز الفصل Patternفواصل الأسطر التالية:
  • حرف الإرجاع ( \r);
  • حرف السطر الجديد (رمز لتقديم الورقة سطرًا واحدًا) ( \n
  • حرف إرجاع إلى أول السطر متبوعًا مباشرة بحرف السطر الجديد ( \r\n);
  • حرف السطر التالي ( \u0085);
  • حرف فاصل الأسطر ( \u2028);
  • رمز فاصل الفقرة ( \u2029)

المجموعات الملتقطة

يتم استخدام مجموعة الالتقاط لحفظ مجموعة الأحرف التي تم العثور عليها لاستخدامها مرة أخرى عند البحث حسب النمط. هذا البناء عبارة عن سلسلة من الأحرف المحاطة بأحرف أولية بين قوسين ( ( )). يتم اعتبار كافة الأحرف الموجودة ضمن المجموعة الملتقطة ككل واحد عند البحث حسب النمط. على سبيل المثال، تقوم مجموعة الالتقاط ( Java) بدمج الحروف Jو aو في وحدة واحدة v. aتقوم مجموعة الالتقاط هذه بالبحث عن كافة تكرارات النموذج Javaفي نص الإدخال. مع كل مباراة، يتم استبدال الأحرف المخزنة السابقة Javaبالأحرف التالية. يمكن دمج المجموعات التي تم التقاطها ضمن مجموعات أخرى تم التقاطها. على سبيل المثال، في التعبير العادي، يتم دمج (Java( language))المجموعة (language)داخل مجموعة (Java). يتم تعيين رقم لكل مجموعة التقاط متداخلة أو غير متداخلة، بدءًا من 1، وينتقل الترقيم من اليسار إلى اليمين. في المثال السابق، (Java( language))تطابقات مجموعة الالتقاط رقم 1 (language)وتطابقات مجموعة الالتقاط رقم 2. في التعبير العادي (a)(b)، (a)تتطابق تطابقات مجموعة الالتقاط رقم 1 ومجموعة (b)الالتقاط رقم 2. التعبيرات العادية في جافا، الجزء 2 - 2يمكن الوصول إلى المطابقات المخزنة بواسطة مجموعات الالتقاط لاحقًا باستخدام المراجع الخلفية. تم تحديده كحرف شرطة مائلة عكسية متبوعًا بحرف رقمي يتوافق مع عدد المجموعة التي يتم التقاطها، ويسمح لك المرجع الخلفي بالإشارة إلى الأحرف الموجودة في النص الذي تم التقاطه بواسطة المجموعة. يؤدي وجود رابط خلفي إلى قيام المطابق بالإشارة إلى نتيجة البحث المخزنة للمجموعة التي تم التقاطها بناءً على الرقم الموجود فيها، ثم استخدام الأحرف من تلك النتيجة لمحاولة إجراء المزيد من البحث. يوضح المثال التالي استخدام المرجع الخلفي للعثور على الأخطاء النحوية في النص: يستخدم java RegexDemo "(Java( language)\2)" "The Java language language" هذا المثال (Java( language)\2)تعبيرًا عاديًا للعثور على خطأ نحوي مع وجود كلمة مكررة languageتتبع مباشرة Javaفي النص المُدخل "The Java language language". يحدد هذا التعبير العادي مجموعتين لالتقاطهما: الرقم 1 – (Java( language)\2), الموافق Java language languageللرقم 2 – (language), الموافق لحرف المسافة متبوعًا بـ language. يسمح المرجع الخلفي \2بإعادة النظر في النتيجة المخزنة للمجموعة رقم 2 بحيث يتمكن المطابق من البحث عن التواجد الثاني للمسافة متبوعًا languageمباشرة بعد التواجد الأول للمسافة و language. نتائج المباراة RegexDemoهي كما يلي:
regex = (Java( language)\2)
input = The Java language language
Found [Java language language] starting at 4 and ending at 25

متطابقات الحدود

في بعض الأحيان تحتاج إلى إجراء مطابقة النمط في بداية السطر، عند حدود الكلمات، في نهاية النص، وما إلى ذلك. يمكنك القيام بذلك عن طريق استخدام أحد أدوات مطابقة حافة الفئة Pattern، وهي عبارة عن بنيات تعبير عادية تبحث عن التطابقات في المواقع التالية:
  • ^: بداية السطر؛
  • $: نهاية الخط؛
  • \b: حدود الكلمة؛
  • \B: حد الكلمة الزائفة؛
  • \A: بداية النص؛
  • \G: نهاية المباراة السابقة؛
  • \Z: نهاية النص، باستثناء فاصل الأسطر الزائدة (إن وجد)؛
  • \z: نهاية النص
يستخدم المثال التالي الحرف ^الأولي لمطابقة الحدود للعثور على الأسطر التي تبدأ بـ The، متبوعة بصفر أو أكثر من أحرف الكلمة: يحدد java RegexDemo "^The\w*" Therefore الحرف ^أن الأحرف الثلاثة الأولى من نص الإدخال يجب أن تتطابق مع أحرف النمط المتتالية و T، والتي يمكن أن يتبعها أي رقم من رموز تشكيل الكلمات. وهنا نتيجة التنفيذ: he
regex = ^The\w*
input = Therefore
Found [Therefore] starting at 0 and ending at 8
ماذا يحدث إذا قمت بتغيير سطر الأوامر إلى java RegexDemo "^The\w*" " Therefore"؟ لن يتم العثور على أي تطابق لأن Thereforeنص الإدخال يسبقه حرف مسافة.

تطابقات ذات طول صفري

في بعض الأحيان، عند العمل باستخدام أدوات مطابقة الحواف، ستواجه مطابقات ذات طول صفري. Совпадение нулевой длиныهي مطابقة لا تحتوي على أية أحرف. يمكن أن تحدث في نص إدخال فارغ، في بداية نص الإدخال، بعد الحرف الأخير من نص الإدخال، وبين أي حرفين من نص الإدخال. من السهل التعرف على المطابقات ذات الطول الصفري لأنها تبدأ وتنتهي دائمًا في نفس الموضع. خذ بعين الاعتبار المثال التالي: java RegExDemo \b\b "Java is" يبحث هذا المثال عن حدين متتاليين من الكلمات، وستبدو النتائج كما يلي:
regex = \b\b
input = Java is
Found [] starting at 0 and ending at -1
Found [] starting at 4 and ending at 3
Found [] starting at 5 and ending at 4
Found [] starting at 7 and ending at 6
نرى العديد من التطابقات ذات الطول الصفري في النتائج. مواضع النهاية هنا أقل بمقدار واحد من مواضع البداية، حيث RegexDemoأنني حددتها في الكود المصدري في القائمة 1 end() – 1. التعبيرات العادية في جافا، الجزء 2 - 3

محددو الكمية

المُحدِّد الكمي عبارة عن بنية تعبير عادية تربط بشكل صريح أو ضمني نمطًا بقيمة رقمية. تحدد هذه القيمة الرقمية عدد مرات البحث عن النمط. ينقسم الكميون إلى جشعين وكسولين وجشعين للغاية:
  • تم تصميم المُحدِّد الكمي الجشع ( ?، *أو +) للعثور على أطول تطابق. يمكن لي أن أسأل X؟ للعثور على حدث واحد أو أقل X، X*للعثور على صفر تكرار أو أكثر X، X+للعثور على حدث واحد أو أكثر X، X{n}للعثور على nتكرارات X، للعثور على تكرارات X{n,}على الأقل (وربما أكثر) ، وللعثور على تكرارات على الأقل ولكن ليس أكثر .nXX{n,m}nmX
  • تم تصميم المُحدِّد الكمي البطيء ( ??أو *?) +?للعثور على أقصر تطابق. يمكنك تحديد X??البحث عن تكرار واحد أو أقل لـ X, X*? للعثور على صفر أو أكثر من تكرارات X، X+?للعثور على واحد أو أكثر من تكرارات X، X{n}?للعثور على nتكرارات X، X{n,}?للعثور على الأقل (وربما أكثر) nمن تكرارات X، X{n,m}?وللعثور على الأقل nولكن ليس أكثر من mتكرارات X.
  • مُحدِّد الكمي الفائق الجشع ( ?+، *+أو ++) يشبه مُحدِّد الكمي الجشع، فيما عدا أن مُحدِّد الكمي الفائق الجشع يقوم بمحاولة واحدة فقط للعثور على أطول تطابق، بينما يمكن لمُحدِّد الكمي الجشع القيام بمحاولات متعددة. يمكن تعيينها X?+للعثور على تكرار واحد أو أقل X، X*+أو للعثور على صفر أو أكثر من تكرارات X، X++أو للعثور على تكرار واحد أو أكثر X، X{n}+أو للعثور على nتكرارات X، أو للعثور على تكرارات X{n,}+على الأقل (وربما أكثر) ، أو للعثور على تكرارات على الأقل ولكن ليس أكثر .nXX{n,m}+ nmX
يوضح المثال التالي استخدام المُحدِّد الكمي الجشع: java RegexDemo .*ox "fox box pox" وإليكم النتائج:
regex = .*ox
input = fox box pox
Found [fox box pox] starting at 0 and ending at 10
يعثر المُحدِّد الكمي الجشع ( .*) على أطول تسلسل من الأحرف التي تنتهي بـ ox. فهو يستهلك نص الإدخال بالكامل ثم يتراجع حتى يكتشف أن نص الإدخال ينتهي بهذه الأحرف. لننظر الآن إلى المُحدِّد الكمي البطيء: java RegexDemo .*?ox "fox box pox" نتائجه:
regex = .*?ox
input = fox box pox
Found [fox] starting at 0 and ending at 2
Found [ box] starting at 3 and ending at 6
Found [ pox] starting at 7 and ending at 10
يقوم المُحدِّد الكمي البطيء ( .*?) بالبحث عن أقصر تسلسل للأحرف المنتهية بـ ox. يبدأ بسلسلة فارغة ويستهلك الأحرف تدريجيًا حتى يجد تطابقًا. ثم يستمر العمل حتى يتم استنفاد نص الإدخال. أخيرًا، دعونا نلقي نظرة على المُحدِّد الكمي الجشع للغاية: java RegexDemo .*+ox "fox box pox" وها هي نتائجه:
regex = .*+ox
input = fox box pox
لا يجد المُحدِّد الكمي الجشع للغاية ( .*+) أي تطابقات لأنه يستهلك كل النص المُدخل ولا يوجد شيء متبقي لمطابقته oxفي نهاية التعبير العادي. وعلى النقيض من محدد الكم الجشع، فإن محدد الكم فائق الجشع لا يتراجع.

تطابقات ذات طول صفري

في بعض الأحيان، عند العمل باستخدام محددات الكمية، ستواجه مطابقات ذات طول صفري. على سبيل المثال، يؤدي استخدام المُحدِّد الكمي الجشع التالي إلى ظهور عدة تطابقات ذات طول صفري: java RegexDemo a? abaa نتائج تشغيل هذا المثال:
regex = a?
input = abaa
Found [a] starting at 0 and ending at 0
Found [] starting at 1 and ending at 0
Found [a] starting at 2 and ending at 2
Found [a] starting at 3 and ending at 3
Found [] starting at 4 and ending at 3
هناك خمس مباريات في نتائج التنفيذ. على الرغم من أن الأحرف الأولى والثالثة والرابعة متوقعة تمامًا (وهي تتوافق مع مواضع الأحرف الثلاثة aفي abaa)، إلا أن الثانية والخامسة قد تفاجئك. ويبدو أنها تشير إلى ما aيتوافق bمع نهاية النص، ولكن في الواقع ليس هذا هو الحال. a?لا يقوم التعبير العادي بالبحث bفي نهاية النص. يبحث عن الحضور أو الغياب a. عندما a?لا يتم العثور عليه a، فإنه يقوم بالإبلاغ عنه كتطابق ذي طول صفري.

تعبيرات العلم المتداخلة

تضع المطابقات بعض الافتراضات الافتراضية التي يمكن تجاوزها عند تجميع التعبير العادي في نمط. سنناقش هذه المسألة لاحقا. يتيح لك التعبير العادي تجاوز أي من الإعدادات الافتراضية باستخدام تعبير علامة متداخل. يتم تحديد بنية التعبير العادي هذه كحرف أولي بين قوسين حول حرف علامة الاستفهام ( ?)، متبوعًا بحرف لاتيني صغير. يفهم الفصل Patternتعبيرات العلامات المتداخلة التالية:
  • (?i): لتمكين مطابقة الأنماط غير الحساسة لحالة الأحرف. على سبيل المثال، عند استخدام أمر ما، java RegexDemo (?i)tree Treehouseفإن تسلسل الأحرف Treeيتطابق مع النمط tree. الافتراضي هو البحث عن نمط حساس لحالة الأحرف.
  • (?x): يسمح باستخدام أحرف المسافات البيضاء والتعليقات التي تبدأ بالحرف الأولي داخل النمط #. سوف يتجاهل المطابق كليهما. على سبيل المثال، java RegexDemo ".at(?x)#match hat, cat, and so on" matterلسلسلة من الأحرف matيتطابق مع النمط .at. افتراضيًا، لا يُسمح بأحرف المسافات البيضاء والتعليقات، وتتعامل معها أداة المطابقة كأحرف مشاركة في البحث.
  • (?s): لتمكين وضع dotall، حيث يتطابق الحرف الأولي النقطي مع فواصل الأسطر بالإضافة إلى أي حرف آخر. java RegexDemo (?s). \nعلى سبيل المثال، سيبحث الأمر عن حرف السطر الجديد. الافتراضي هو عكس dotall: لن يتم العثور على فواصل الأسطر. Java RegexDemo . \nعلى سبيل المثال، لن يجد الأمر حرف السطر الجديد.
  • (?m): تمكين وضع الخطوط المتعددة، حيث ^يطابق بداية ونهاية $كل سطر. على سبيل المثال، java RegexDemo "(?m)^abc$" abc\nabcيبحث عن كلا التسلسلين في نص الإدخال abc. افتراضيًا، يتم استخدام وضع السطر الفردي: ^يطابق بداية النص المُدخل بالكامل، $ويطابق نهايته. على سبيل المثال، java RegexDemo "^abc$" abc\nabcيتم إرجاع استجابة تفيد بعدم وجود تطابقات.
  • (?u): لتمكين محاذاة حالة الأحرف الحساسة لـ Unicode. تسمح هذه العلامة، عند استخدامها مع (?i)، بمطابقة الأنماط غير الحساسة لحالة الأحرف وفقًا لمعيار Unicode. الإعداد الافتراضي هو البحث عن الأحرف الحساسة لحالة الأحرف وأحرف US-ASCII فقط.
  • (?d): تمكين وضع السلسلة بنمط Unix، حيث يتعرف المطابق على الأحرف الأولية في السياق .، ^وفاصل $الأسطر فقط \n. الوضع الافتراضي هو وضع سلسلة نمط غير Unix: يتعرف المطابق، في سياق الأحرف الأولية المذكورة أعلاه، على جميع محددات الأسطر.
تشبه تعبيرات العلامات المتداخلة المجموعات الملتقطة لأن أحرفها محاطة بأحرف أولية بين قوسين. على عكس المجموعات الملتقطة، تعد تعبيرات العلامات المتداخلة مثالاً على المجموعات غير الملتقطة، وهي عبارة عن بنية تعبير عادية لا تلتقط أحرف النص. يتم تعريفها على أنها تسلسلات من الأحرف محاطة بأحرف أولية بين قوسين.
تحديد تعبيرات العلم المتداخلة المتعددة
من الممكن تحديد تعبيرات أعلام متداخلة متعددة في التعبير العادي إما عن طريق وضعها جنبًا إلى جنب ( (?m)(?i))) أو وضع الأحرف التي تحددها بشكل تسلسلي ( (?mi)).

خاتمة

ربما تكون قد أدركت الآن، أن التعبيرات العادية مفيدة للغاية وتصبح أكثر فائدة عندما تتقن الفروق الدقيقة في تركيبها. لقد عرّفتك حتى الآن على أساسيات التعبيرات العادية و Pattern. في الجزء الثاني، سنلقي نظرة أعمق على Regex API Patternونستكشف Matcherطرق PatternSyntaxException. سأعرض لك أيضًا تطبيقين عمليين لـ Regex API يمكنك استخدامهما على الفور في برامجك. التعبيرات العادية في جافا، الجزء 3 التعبيرات العادية في جافا، الجزء 4 التعبيرات العادية في جافا، الجزء 5
تعليقات
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION