Bir Değer Hatası nasıl yükseltilir?


115

Bir dizedeki belirli bir karakterin en büyük dizinini bulan bu koda sahibim, ancak ValueErrorbelirtilen karakter bir dizede bulunmadığında a yükseltmesini istiyorum .

Yani bunun gibi bir şey:

contains('bababa', 'k')

şu şekilde sonuçlanır:

ValueError: could not find k in bababa

Bunu nasıl yapabilirim?

İşte fonksiyonum için mevcut kod:

def contains(string,char):
  list = []

  for i in range(0,len(string)):
      if string[i] == char:
           list = list + [i]

  return list[-1]

5
Aynı bunun gibi, ValueError ()
değerini artırın

@ user531225: Benimkini silebilmem için başka bir cevabı kabul edebilir misin? Teşekkürler :)
pyfunc

@ THC4k: O kadar tuhaf ki, sayım yerine en sağdaki oluşumun konumunu döndürüyor.
John Machin

@ErikAllik: Tabii ki yaptı - StackOverflow'a gönderi paylaştı. Bunun derdi ne?
Michael Scheper

Yanıtlar:


178

raise ValueError('could not find %c in %s' % (ch,str))


2
Mesajı kullanmak istemiyorsanız, raise ValueErrorbunun yerine kullanabileceğinizi biliyor muydunuz raise ValueError()?
Tomasz Gandor

27

İşte kodunuzun hala çalışan revize edilmiş bir sürümü ve ayrıca ValueErroristediğiniz şekilde nasıl yükseltileceğini gösteriyor . Bu arada, sanırım find_last(), find_last_index()ya da benzeri bir şey bu işlev için daha açıklayıcı bir isim olurdu. Muhtemel karışıklığa ek olarak, Python'un __contains__()üyelik testi açısından biraz farklı bir şey yapan bir kapsayıcı nesne yöntemine zaten sahip olması gerçeğidir .

def contains(char_string, char):
    largest_index = -1
    for i, ch in enumerate(char_string):
        if ch == char:
            largest_index = i
    if largest_index > -1:  # any found?
        return largest_index  # return index of last one
    else:
        raise ValueError('could not find {!r} in {!r}'.format(char, char_string))

print(contains('mississippi', 's'))  # -> 6
print(contains('bababa', 'k'))  # ->
Traceback (most recent call last):
  File "how-to-raise-a-valueerror.py", line 15, in <module>
    print(contains('bababa', 'k'))
  File "how-to-raise-a-valueerror.py", line 12, in contains
    raise ValueError('could not find {} in {}'.format(char, char_string))
ValueError: could not find 'k' in 'bababa'

Güncelleme - Çok daha basit bir yol

Vaov! İşte çok daha özlü bir versiyon - esasen tek satırlık - bu aynı zamanda muhtemelen daha hızlıdır çünkü ilk eşleşen karakter [::-1]için ileri arama yapmadan önce dizeyi ters çevirir (üzerinden ) ve bunu hızlı yerleşik dize yöntemini kullanarak yapar. . Asıl sorunuzla ilgili olarak, kullanımla birlikte gelen hoş bir küçük bonus kolaylık , karakter alt dizesi bulunmadığında zaten a'yı yükseltmesidir , bu nedenle bunun olması için ek bir şey gerekmez.index()index()ValueError

İşte hızlı bir birim testi ile birlikte:

def contains(char_string, char):
    #  Ending - 1 adjusts returned index to account for searching in reverse.
    return len(char_string) - char_string[::-1].index(char) - 1

print(contains('mississippi', 's'))  # -> 6
print(contains('bababa', 'k'))  # ->
Traceback (most recent call last):
  File "better-way-to-raise-a-valueerror.py", line 9, in <module>
    print(contains('bababa', 'k'))
  File "better-way-to-raise-a-valueerror", line 6, in contains
    return len(char_string) - char_string[::-1].index(char) - 1
ValueError: substring not found

2. işlev: OP bir fordöngüye ihtiyaç duyar / ister . 1. işlev: FAIL for contains('foo', 'f').
John Machin

1
@John Machin: 1. işlevde bulduğunuz hata düzeltildi, dikkatimi çektiğiniz için teşekkürler. OP'nin sorusunda veya altındaki yorumlarda for, kendi kodlarında görünmesine rağmen, bir cevapta bir döngüye ihtiyaç duyduklarını veya istediklerini belirten hiçbir şey görmüyorum . Her neyse benim 1 fonksiyon gösterir bunları nasıl raisebir ValueErrorkarakter olan bulunamazsa zaman olduğu onlar ne sordu. ve a bağlamında nasıl yapılacağını gösterdim for. Herhangi bir fornedenle isteseler bile , bence diğerleri 2. sürümü en azından biraz ilginç bulabilir.
martineau

"Döngü için kullanmak istiyorum :-)", @pyfunc tarafından şimdi silinen cevaba erken bir yorumdu
John Machin

1
@John Machin: Yapmadığım ve göremediğim, silinmiş cevapların yorumlarındaki talepleri yerine getirmediğim için sorumlu tutulabileceğimi sanma. Ancak, benim 2 işlevi kullanmaz olsa fordöngü, bu mu bir bakıma gerçek ile ilgili soruyu nasıl yanıtlamak raisebir ValueErroryani sizin için yapar başka bir şey arayarak - karakter dizesi bulundu değilken. Ayrıca, OP'nin for, bir yan forçözüm gördükten veya daha sonra Python'a daha aşina olduktan sonra-sabitlemelerini veya her ne ise , üstesinden gelebileceği ihtimali de var .
martineau

12
>>> def contains(string, char):
...     for i in xrange(len(string) - 1, -1, -1):
...         if string[i] == char:
...             return i
...     raise ValueError("could not find %r in %r" % (char, string))
...
>>> contains('bababa', 'k')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 5, in contains
ValueError: could not find 'k' in 'bababa'
>>> contains('bababa', 'a')
5
>>> contains('bababa', 'b')
4
>>> contains('xbababa', 'x')
0
>>>

4
>>> response='bababa'
...  if "K" in response.text:
...     raise ValueError("Not found")

1
Bu kod soruyu yanıtlayabilirken, sorunun nasıl ve / veya neden çözüldüğüne ilişkin ek içerik sağlamak, yanıtın uzun vadeli değerini artıracaktır.
Donald Duck
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.