स्ट्रिंग में वर्णों की सूची निकालना


217

मैं अजगर में एक स्ट्रिंग में पात्रों को निकालना चाहता हूं:

string.replace(',', '').replace("!", '').replace(":", '').replace(";", '')...

लेकिन मेरे पास कई किरदार हैं जिन्हें मुझे हटाना है। मैंने एक सूची के बारे में सोचा

list = [',', '!', '.', ';'...]

लेकिन मैं listपात्रों को बदलने के लिए कैसे उपयोग कर सकता हूं string?


6
विभिन्न समाधानों और एक अच्छी तुलना के लिए stackoverflow.com/questions/1919096/… देखें ।
Martijn de Milliano

यह अफ़सोस की बात है कि पायथन (जिसमें शामिल बैटरी के साथ आने के लिए कहा गया है) इस उपयोग के मामले को बॉक्स से बाहर नहीं करता है। PHP का कार्य str_replace करता है - आप पहले तर्क के रूप में एक सरणी और दूसरे के रूप में एक स्ट्रिंग ( php.net/manual/pl/function.str-replace.php ) पास कर सकते हैं ।
JustAC0der

जवाबों:


265

यदि आप python2 का उपयोग कर रहे हैं और आपके इनपुट स्ट्रिंग्स हैं (यूनिकोड नहीं), तो सबसे अच्छा तरीका है str.translate:

>>> chars_to_remove = ['.', '!', '?']
>>> subj = 'A.B!C?'
>>> subj.translate(None, ''.join(chars_to_remove))
'ABC'

अन्यथा, विचार करने के लिए निम्नलिखित विकल्प हैं:

उ। विषय को चार वर्ण से अलग करें, अवांछित वर्णों और joinपरिणामी सूची को छोड़ें :

>>> sc = set(chars_to_remove)
>>> ''.join([c for c in subj if c not in sc])
'ABC'

(ध्यान दें कि जनरेटर संस्करण ''.join(c for c ...) कम कुशल होगा)।

B. मक्खी पर और re.subएक खाली स्ट्रिंग के साथ एक नियमित अभिव्यक्ति बनाएँ :

>>> import re
>>> rx = '[' + re.escape(''.join(chars_to_remove)) + ']'
>>> re.sub(rx, '', subj)
'ABC'

( re.escapeयह सुनिश्चित करता है कि अक्षर नियमित अभिव्यक्ति को तोड़ेंगे ^या ]नहीं तोड़ेंगे)।

सी। मैपिंग संस्करण काtranslate उपयोग करें :

>>> chars_to_remove = [u'δ', u'Γ', u'ж']
>>> subj = u'AжBδCΓ'
>>> dd = {ord(c):None for c in chars_to_remove}
>>> subj.translate(dd)
u'ABC'

पूर्ण परीक्षण कोड और समय:

#coding=utf8

import re

def remove_chars_iter(subj, chars):
    sc = set(chars)
    return ''.join([c for c in subj if c not in sc])

def remove_chars_re(subj, chars):
    return re.sub('[' + re.escape(''.join(chars)) + ']', '', subj)

def remove_chars_re_unicode(subj, chars):
    return re.sub(u'(?u)[' + re.escape(''.join(chars)) + ']', '', subj)

def remove_chars_translate_bytes(subj, chars):
    return subj.translate(None, ''.join(chars))

def remove_chars_translate_unicode(subj, chars):
    d = {ord(c):None for c in chars}
    return subj.translate(d)

import timeit, sys

def profile(f):
    assert f(subj, chars_to_remove) == test
    t = timeit.timeit(lambda: f(subj, chars_to_remove), number=1000)
    print ('{0:.3f} {1}'.format(t, f.__name__))

print (sys.version)
PYTHON2 = sys.version_info[0] == 2

print ('\n"plain" string:\n')

chars_to_remove = ['.', '!', '?']
subj = 'A.B!C?' * 1000
test = 'ABC' * 1000

profile(remove_chars_iter)
profile(remove_chars_re)

if PYTHON2:
    profile(remove_chars_translate_bytes)
else:
    profile(remove_chars_translate_unicode)

print ('\nunicode string:\n')

if PYTHON2:
    chars_to_remove = [u'δ', u'Γ', u'ж']
    subj = u'AжBδCΓ'
else:
    chars_to_remove = ['δ', 'Γ', 'ж']
    subj = 'AжBδCΓ'

subj = subj * 1000
test = 'ABC' * 1000

profile(remove_chars_iter)

if PYTHON2:
    profile(remove_chars_re_unicode)
else:
    profile(remove_chars_re)

profile(remove_chars_translate_unicode)

परिणाम:

2.7.5 (default, Mar  9 2014, 22:15:05) 
[GCC 4.2.1 Compatible Apple LLVM 5.0 (clang-500.0.68)]

"plain" string:

0.637 remove_chars_iter
0.649 remove_chars_re
0.010 remove_chars_translate_bytes

unicode string:

0.866 remove_chars_iter
0.680 remove_chars_re_unicode
1.373 remove_chars_translate_unicode

---

3.4.2 (v3.4.2:ab2c023a9432, Oct  5 2014, 20:42:22) 
[GCC 4.2.1 (Apple Inc. build 5666) (dot 3)]

"plain" string:

0.512 remove_chars_iter
0.574 remove_chars_re
0.765 remove_chars_translate_unicode

unicode string:

0.817 remove_chars_iter
0.686 remove_chars_re
0.876 remove_chars_translate_unicode

(एक साइड नोट के रूप में, यह आंकड़ा remove_chars_translate_bytesहमें इस बात का संकेत दे सकता है कि उद्योग इतने लंबे समय तक यूनिकोड को अपनाने के लिए अनिच्छुक क्यों था)।


1
दूसरी विधि एक त्रुटि उठाती है TypeError: translate() takes exactly one argument (2 given)। जाहिर तौर पर यह एक तर्क के रूप में तय होता है।
एनटोनवी

@antonavy - दूसरा समाधान काम करता है - लेकिन केवल स्ट्रिंग यूनिकोड नहीं है (जिसके लिए एक अलग अनुवाद () की आवश्यकता है)
FuzzyAmi

112

आप उपयोग कर सकते हैं str.translate():

s.translate(None, ",!.;")

उदाहरण:

>>> s = "asjo,fdjk;djaso,oio!kod.kjods;dkps"
>>> s.translate(None, ",!.;")
'asjofdjkdjasooiokodkjodsdkps'

19
@ thg435: किसी ने भी इसके लिए नहीं कहा, लेकिन वैसे भी:s.translate(dict.fromkeys(map(ord, u",!.;")))
स्वेन मार्नाच

2
यह (और @ प्रवीणगोलाकोटा का) एक साथ उत्तर ठीक वैसा ही है जैसा @ लोरा ने मांगा था और उसे पसंदीदा उत्तर होना चाहिए।
होब्स

7
क्यों python3: TypeError: अनुवाद () बिल्कुल एक तर्क (2 दिया) लेता है
Gank

2
@Gank: unicode.translate()विधि की विधि की तुलना में भिन्न पैरामीटर हैं str.translate()। यूनिकोड ऑब्जेक्ट के लिए उपरोक्त टिप्पणी में संस्करण का उपयोग करें।
स्वेन मार्नाच

@SvenMarnach नक्शा (ord, u ";?;?")) क्या है? और क्या आप यूनिकोड के लिए खड़े हैं?
.११


16
''.join(c for c in myString if not c in badTokens)

इसी तरह के मामलों में उपयोगी चार्ट और स्ट्रिंग्स पर आधारित नहीं है +1
वुल्फ

12

यदि आप python3 का उपयोग कर रहे हैं और translateसमाधान की तलाश कर रहे हैं - फ़ंक्शन बदल गया था और अब 2 के बजाय 1 पैरामीटर लेता है।

वह पैरामीटर एक तालिका है (डिक्शनरी हो सकती है) जहां प्रत्येक कुंजी चरित्र को खोजने के लिए यूनिकोड ऑर्डिनल (इंट) है और मूल्य प्रतिस्थापन है (कुंजी को मैप करने के लिए एक यूनिकोड ऑर्डिनल या स्ट्रिंग हो सकता है)।

यहाँ एक उपयोग उदाहरण है:

>>> list = [',', '!', '.', ';']
>>> s = "This is, my! str,ing."
>>> s.translate({ord(x): '' for x in list})
'This is my string'

8

रेगेक्स का उपयोग कर एक और दृष्टिकोण:

''.join(re.split(r'[.;!?,]', s))

7

साधारण लूप क्यों नहीं?

for i in replace_list:
    string = string.replace(i, '')

इसके अलावा, सूचियों के नाम 'सूची' से बचें। यह अंतर्निहित फ़ंक्शन को ओवरराइड करता है list


6

आप कुछ इस तरह का उपयोग कर सकते हैं

def replace_all(text, dic):
  for i, j in dic.iteritems():
    text = text.replace(i, j)
  return text

यह कोड मेरा अपना नहीं है और यहीं से इसका एक बेहतरीन लेख आया है और ऐसा करने में इसकी गहराई है


3

इसके अलावा UTF-8 एक्सेंट को हटाने पर एक दिलचस्प विषय उनके मानक गैर-उच्चारण चार्ट में एक स्ट्रिंग को परिवर्तित करता है:

अजगर यूनिकोड स्ट्रिंग में लहजे को हटाने का सबसे अच्छा तरीका क्या है?

विषय से कोड निकालने:

import unicodedata

def remove_accents(input_str):
    nkfd_form = unicodedata.normalize('NFKD', input_str)
    return u"".join([c for c in nkfd_form if not unicodedata.combining(c)])

3

शायद जो आप चाहते हैं उसे प्राप्त करने के लिए एक अधिक आधुनिक और कार्यात्मक तरीका:

>>> subj = 'A.B!C?'
>>> list = set([',', '!', '.', ';', '?'])
>>> filter(lambda x: x not in list, subj)
'ABC'

कृपया ध्यान दें कि इस विशेष उद्देश्य के लिए यह काफी ओवरकिल है, लेकिन एक बार जब आपको अधिक जटिल परिस्थितियों की आवश्यकता होती है, तो फ़िल्टर काम आता है


यह भी ध्यान दें कि यह आसानी से सूची समझ के साथ किया जा सकता है, जो कि मेरी राय में अधिक पायथोनिक है।
दंगे हुए

3

सरल तरीका,

import re
str = 'this is string !    >><< (foo---> bar) @-tuna-#   sandwich-%-is-$-* good'

// condense multiple empty spaces into 1
str = ' '.join(str.split()

// replace empty space with dash
str = str.replace(" ","-")

// take out any char that matches regex
str = re.sub('[!@#$%^&*()_+<>]', '', str)

उत्पादन:

this-is-string--foo----bar--tuna---sandwich--is---good



1

मुझे लगता है कि यह काफी सरल है और करेंगे!

list = [",",",","!",";",":"] #the list goes on.....

theString = "dlkaj;lkdjf'adklfaj;lsd'fa'dfj;alkdjf" #is an example string;
newString="" #the unwanted character free string
for i in range(len(TheString)):
    if theString[i] in list:
        newString += "" #concatenate an empty string.
    else:
        newString += theString[i]

यह करने का एक तरीका है। लेकिन अगर आप उन पात्रों की सूची रखने से थक गए हैं जिन्हें आप हटाना चाहते हैं, तो आप वास्तव में उन स्ट्रिंग्स के क्रम संख्या का उपयोग करके कर सकते हैं जिनके माध्यम से आप इसे पुनरावृत्त करते हैं। क्रम संख्या उस वर्ण का एससीआई मान है। एक चार के रूप में एससीआई संख्या ४ci है और लोअर केस जेड के लिए एससीआई संख्या १२२ है।

theString = "lkdsjf;alkd8a'asdjf;lkaheoialkdjf;ad"
newString = ""
for i in range(len(theString)):
     if ord(theString[i]) < 48 or ord(theString[i]) > 122: #ord() => ascii num.
         newString += ""
     else:
        newString += theString[i]

0

इन दिनों मैं स्कीम में गोता लगा रहा हूं, और अब मुझे लगता है कि मैं अच्छा प्रदर्शन कर रहा हूं। HAHAHA। बस कुछ नए तरीके साझा करें:

सबसे पहले, इसे बाहर निकालें

print eval('string%s' % (''.join(['.replace("%s","")'%i for i in replace_list])))

दूसरा, इसे फिर से भरना

def repn(string,replace_list):
    if replace_list==[]:
        return string
    else:
        return repn(string.replace(replace_list.pop(),""),replace_list)

print repn(string,replace_list)

अरे, निराश मत करो। मैं सिर्फ कुछ नया विचार साझा करना चाहता हूं।


0

मैं इसके लिए एक समाधान के बारे में सोच रहा हूं। पहले मैं एक सूची के रूप में स्ट्रिंग इनपुट बनाऊंगा। फिर मैं सूची के आइटमों को बदल दूंगा। फिर ज्वाइन कमांड का उपयोग करके, मैं एक स्ट्रिंग के रूप में सूची वापस करूंगा। कोड इस तरह हो सकता है:

def the_replacer(text):
    test = []    
    for m in range(len(text)):
        test.append(text[m])
        if test[m]==','\
        or test[m]=='!'\
        or test[m]=='.'\
        or test[m]=='\''\
        or test[m]==';':
    #....
            test[n]=''
    return ''.join(test)

यह स्ट्रिंग से कुछ भी निकाल देगा। तुम उसके बारे में क्या सोचते हो?


0

यहाँ एक more_itertoolsदृष्टिकोण है:

import more_itertools as mit


s = "A.B!C?D_E@F#"
blacklist = ".!?_@#"

"".join(mit.flatten(mit.split_at(s, pred=lambda x: x in set(blacklist))))
# 'ABCDEF'

यहाँ हम आइटम में पाए गए पर विभाजित करते हैं blacklist, परिणामों को समतल करते हैं और स्ट्रिंग में शामिल होते हैं।


0

पायथन 3, एकल पंक्ति सूची समझ कार्यान्वयन।

from string import ascii_lowercase # 'abcdefghijklmnopqrstuvwxyz'
def remove_chars(input_string, removable):
  return ''.join([_ for _ in input_string if _ not in removable])

print(remove_chars(input_string="Stack Overflow", removable=ascii_lowercase))
>>> 'S O'

0

हटाना *%,&@! नीचे से स्ट्रिंग:

s = "this is my string,  and i will * remove * these ** %% "
new_string = s.translate(s.maketrans('','','*%,&@!'))
print(new_string)

# output: this is my string  and i will  remove  these  
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.