यह निर्धारित करने के लिए कि वर्तमान वर्ण एक अक्षर है


9

मैं यह कैसे निर्धारित कर सकता हूं कि यदि वर्तमान वर्ण एक अक्षर (एक वर्णमाला वर्ण) है (यानी, [:alpha:]रेक्सएक्सपियन धारणाओं में वाक्य रचना वर्ग का है)। मैं नीचे एक साधारण फ़ंक्शन लिखना चाहूंगा:

(defun test-letter () (interactive)
(if char-after-is-a-letter
    (message "This is a letter")
    (message "This is not a letter")
    )
)

अपडेट दुर्भाग्य से अक्षरों के वर्ग और वाक्यविन्यास वर्ग की समानता के बारे में मेरी धारणा [:alpha:]झूठी प्रतीत होती है।

जवाबों:


9

यूनिकोड चार गुणों का उपयोग करें

यह निश्चित रूप से काम करना चाहिए:

(memq (get-char-code-property (char-after) 'general-category)
      '(Ll Lu Lo Lt Lm Mn Mc Me Nl))

एक बोनस के रूप में यह भी तेजी से होना चाहिए looking-at


Emacs यूनिकोड मानक द्वारा निर्दिष्ट सभी वर्ण गुणों को संग्रहीत करता है। वे साथ सुलभ हैं get-char-code-property। विशेष रूप से, general-categoryसंपत्ति निर्दिष्ट करती है कि कौन से अक्षर अक्षर हैं ( Llलोअरकेस हैं, Luअपरकेस हैं, और मुझसे नहीं पूछें कि अन्य क्या हैं)।


बहुत धन्यवाद, यह समस्या को हल करता है ۱۲۳۴۵۶۷۸۹۰लेकिन कुछ सच्चे-नकारात्मक हैं, जैसे अरबी या हिब्रू एलेफ: א, ا
नाम

@ नाम तय हुआ। दुबारा प्रयास करें।
मालाबार

2
फिर से धन्यवाद। मैंने इसे विभिन्न वर्णमालाओं के साथ जांचा और यह काम करता है। एकमात्र अपवाद जो मुझे मिला वह कुछ एशियाई वर्णमाला जैसे चीनी en.wikipedia.org/wiki/Chinese_numeral या Japanese en.wikipedia.org/wiki/J जींस_numeral के साथ है । उदाहरण के लिए जापानी में संख्या के रूप में माना जाता है 5। आपका कोड इसे एक पत्र मानता है। शायद यह एक पत्र है (जैसे रोमन संख्या में v)। हो सकता है कि कोई ऐसा व्यक्ति जो जापानी से परिचित हो, वह इसे सत्यापित कर सकता है।
नाम

1
अंग्रेजी शब्द की तरह है five, इसलिए यह एक पत्र है। पांच शब्द के बजाय 5 नंबर लिखते समय वे 5अंग्रेजी की तरह ही इस्तेमाल करते हैं ।
मुइर

8

EDIT: यह उत्तर 25.5 (जहां बग को ठीक किया गया था) में पूरी तरह से मान्य होना चाहिए । पुराने संस्करणों के लिए, अन्य विकल्प का उपयोग करें ।


यह आपको बताना चाहिए कि क्या वर्तमान चार पत्र है, और किसी भी भाषा में काम करना चाहिए।

 (looking-at-p "[[:alpha:]]")

बहुत धन्यवाद, मैं looking-at-pआपके समाधान में इस्तेमाल किए गए और looking-atदूसरे उत्तर में अंतर के बारे में उत्सुक हूं ।
नाम

1
दो फ़ंक्शन समान हैं, सिवाय इसके कि looking-at-pमैच डेटा सेट नहीं है।
17

1
@ नाम-ए-पी एक शुद्ध विधेय के करीब है, क्योंकि यह मैच डेटा सेट नहीं करता है। यदि आपने पहले खोज-फ़ॉरवर्ड match-string(और उसके कई भाई-बहनों) की तरह कुछ किया है, तो खोज का परिणाम वापस आ जाएगा। इस बीच, गैर-विधेय संस्करण के साथ, मैच-स्ट्रिंग लुक-अप मैच का परिणाम लौटाएगा।
मालाबार

5

मुझे लगता है कि आप इससे दूर हो सकते हैं:

(defun test-letter ()
  (interactive)
  (let ((char (char-after)))
    (if (and (eq (char-syntax char) ?w)
             (or (> char ?9)
                 (< char ?1)))
        (message "This is a letter")
      (message "This is not a letter"))))

अपडेट करें

यह एक कम कुशल है, लेकिन आप जो चाहते हैं उसके करीब है:

(defun test-letter ()
  (interactive)
  (if (looking-at "[a-z-A-Z]")
      (message "This is a letter")
    (message "This is not a letter")))

धन्यवाद, एक संभावित समस्या: यह फ़ंक्शन अंकों (123 ...) को एक पत्र मानता है।
नाम

आसानी से ठीक होने योग्य।
abo-abo

बहुत धन्यवाद फिर से। एक और गलत सकारात्मक: यह मानता है ۹(यानी, भारतीय अंक 9) या ٪एक पत्र के रूप में।
नाम

1
आपका पहला समाधान ग्रीक अक्षरों (जैसे ζया α) के साथ ठीक था , लेकिन अपडेट नहीं है।
नाम

लेकिन दोनों का संयोजन एक घनिष्ठ समाधान है।
नाम

2

यदि आप राष्ट्रीय पात्रों और यूनिकोड चरित्र वर्गों के सटीक उपचार के बारे में बहुत चिंतित थे, तो एकमात्र उपाय जो मैं अब तक पा रहा था वह पायथन regexपुस्तकालय है । दोनों grepऔर Perl(मेरे बोलना आश्चर्य करने के लिए!) काम ठीक से नहीं किया।

तो, आप इसके बाद की नियमित अभिव्यक्ति हैं \p{L}। इसे यूनिकोड प्रॉपर्टी शॉर्टहैंड संस्करण के रूप में जाना जाता है, पूर्ण संस्करण \p{Letter}या भी है p\{General_Category=Letter}Letterअपने आप में एक समग्र वर्ग है, लेकिन मैं विवरण में नहीं जाऊंगा, सबसे अच्छा संदर्भ जो मुझे इस विषय पर मिल सकता है

पायथन लाइब्रेरी भाषा में बिल्ट-इन नहीं है (यह बिल्ट-इन reलाइब्रेरी का एक विकल्प है )। इसलिए, आपको इसे स्थापित करने की आवश्यकता होगी, उदाहरण के लिए:

# pip install regex

फिर, आप इसे इस तरह इस्तेमाल कर सकते हैं:

import regex
>>> regex.match(ur'\p{L}+', u'۱۲۳۴۵۶۷۸۹۰')
>>> regex.match(ur'\p{L}+', u'абвгд')
<regex.Match object; span=(0, 5), match=u'\u0430\u0431\u0432\u0433\u0434'>
>>> regex.match(ur'\p{L}+', u'123')
>>> regex.match(ur'\p{L}+', u'abcd')
<regex.Match object; span=(0, 4), match=u'abcd'>
>>> 

आप इस स्क्रिप्ट को कहीं भी रख सकते हैं जहाँ आप इसे एक्सेस कर सकते हैं:

#!/usr/bin/env python
import regex
import sys

if __name__ == "__main__":
    for match in regex.finditer(ur'\p{L}+', sys.argv[1].decode('utf-8')):
        print match.string

और इसे Emacs से इस तरह से कॉल करें (मान लीजिए कि आपने इस स्क्रिप्ट को सहेज लिया है ~/bin):

(defun unicode-character-p ()
  (interactive)
  (let* ((current (char-after (point)))
         (result (shell-command-to-string
                  (format "~/bin/is-character.py '%c'" current))))
    (message
     (if (string= result "") "Character %c isn't a letter"
        "Character %c is a letter")
     current)))
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.