python - 一个简单的 IF 算法的问题:如何检测一个或多个元素不存在?
问题描述
新更新 这是主窗口。它包括根据抓取的结果在每个文本旁边显示一个绿色图标(正确执行抓取)或一个红色图标(抓取错误)。然后基本上,有一个带有问号的图标被红色或绿色图标替换。除了图标更改之外,还会显示错误消息(带有异常的错误消息包含在另一个外部文件中,我用于抓取)。由于导入的两个 py 脚本(或者更确切地说是它们的函数),执行了抓取。它们是 msg1 = Scraping_Nome_Campionati.scraping_nome_campionati_e_tor 和 msg2 = Scraping_Nome_Squadre_MIO.scraping_nome_squadre_e_tor()
def do_scraping():
msg1 = Scraping_Nome_Campionati.scraping_nome_campionati_e_tor()
if msg1:
message1.configure(text=msg1)
message1.configure(foreground="red")
vuoto_elenco_campionati.config(image=render7)
else:
vuoto_elenco_campionati.config(image=render8)
message1.configure(foreground="green")
msg2 = Scraping_Nome_Squadre_MIO.scraping_nome_squadre_e_tor()
if msg2:
message2.configure(text=msg2)
message2.configure(foreground="red")
vuoto_elenco_squadre.config(image=render7)
else:
vuoto_elenco_squadre.config(image=render8)
message2.configure(foreground="green")
button = Button(test_scraping, text="Avvia", bg='#e95420', foreground='white', command=do_scraping)
button.place(x=116, y=512)
两个外部文件中的抓取是这样进行的(我只携带一个文件作为示例)
#example
driver.minimize_window()
driver.get("web site")
Element1=driver.find_element_by_class_name("name class")
Element1_text = Element1.text
#insert in database
con = sqlite3.connect('/dababase')
cursor = con.cursor()
records_added_Risultati = 0
Values = ((Element1_text,), (Element2_text,))
sqlite_insert_query = 'INSERT INTO xxxxx VALUES (?);'
count = cursor.executemany(sqlite_insert_query, Values)
con.commit()
#The error messages are contained in this external scraping file,
# and NOT in the main window with icons
except NoSuchElementException:
return "FAILED (NoSuchElementException)"
except NameError:
return "FAILED (Name Error)"
except ValueError:
return "FAILED (ValueError)"
if records_added_Risultati == 0:
return "FAILED: 0 record scraping"
Campionati_per_controllo_errori = [Element1_text, Element2_text]
if any(Campionati_per_controllo_errori):
return "FAILED (manca 1 campionato)"
问题:所以回顾一下,问题是当抓取正确完成时(抓取和数据库插入),我仍然得到红色错误图标+错误消息。我设置了一种错误类型,以确保“如果没有正确执行抓取,即使只有 1 个,则必须打印错误”,也就是说,如果 20 个文本中的 19 个正确下载,则必须出现错误及其消息. 问题是:即使您抓取了 20 条文本并且一切都正确完成,我也会收到一条消息,指出存在错误并且文本尚未被抓取。
旧更新
如何编码以下内容:
“如果一个或多个”这些元素没有被检测到,那么我会收到一条警告消息。通过警告消息,我的意思是万一有一个抓取问题导致,不是错误,而只是一个空的结果。这样一个元素不会被刮掉,但其他元素会被刮掉。
如果未检测到所有内容,是否会显示警告消息?
所以我需要两种类型的代码。
#example
driver.minimize_window()
driver.get("web site")
Element1=driver.find_element_by_class_name("name class")
Element1 = Element1text
if Element1 or Element2 or Element3 or Element4 or Element5 = no scraping:
return "error"
if Element1, Element2, Element3, Element4, Element5 = no scraping:
return "error"
UPDATE 元素是使用 Selenium 抓取并保存在数据库中的数据。例如它们是这样的:
#Element1
driver.get("site")
for Element1 in driver.find_elements(By.CSS_SELECTOR, xxxxxx'][class^='rxxxxxx']"):
Element1_text = Element1.text
count = cursor.execute(sqlite_insert_query, (Element1_text,))
print(Element1_text)
driver.close
#insert in database
con = sqlite3.connect('/dababase')
cursor = con.cursor()
records_added_Risultati = 0
Values = ((Element1_text,), (Element2_text,))
sqlite_insert_query = 'INSERT INTO xxxxx VALUES (?);'
count = cursor.executemany(sqlite_insert_query, Values)
con.commit()
解决方案
从文档中:
全部(可迭代)
如果可迭代对象的所有元素都为真(或可迭代对象为空),则返回 True。
任何(可迭代)
如果可迭代的任何元素为真,则返回真。如果可迭代对象为空,则返回 False。
现在您只需要从您的元素中创建一个可迭代对象,这非常简单:
some_iterable = [Element1, Element2, Element3, Element4, Element5]
if any(some_iterable): # Like using or on all of them!
return "error"
if all(some_iterable): # Like using and on all of them!
return "error"
现在我们有最后一个问题!元素需要具有固有的真值,它们需要被评估为真或假。正如@Prophet在他的回答中指出的那样,使用driver.find_elements_by_class_name
而不是driver.find_element_by_class_name
(区别在于 ELEMENTS 而不是单个 ELEMENT)可以实现这一点,因为如果找不到具有该类名的元素,它会提供一个空数组(评估为 False)。
如果找到该类元素的一个实例,您将得到一个仅包含该元素的数组,您可以按如下方式使用它Element1[0]
:如果发现多个元素,如预期的那样,您将拥有它们的数组,因此您需要相应地处理它们。
编辑:更多解释。
any(some_iterable)
相当于:
Element1 or Element2 or Element3 or Element4 or Element5
这里。
all(some_iterable)
相当于:
Element1 and Element2 and Element3 and Element4 and Element5
现在您可能会问自己为什么Element1 and Element2 and Element3 and Element4 and Element5
甚至可以工作!答案是,如果元素是[]
或None
,它们在运算符 ( and
) 和 ( or
) 下的计算结果为 False,导致整个表达式计算结果为 False。您可以在此处的 if 语句中阅读有关 False 的更多信息。
您可以if any(some_iterable)
在某种程度上认为“如果 some_iterable 中的任何元素存在并且非零”,并且if any(some_iterable)
说“如果 some_iterable 中的所有元素都存在并且它们都非零”。
实际上,它比这更复杂(很多事情都返回 false,而不仅仅是None
和[]
)0
,但你明白了。
更新了对更新问题的答案。
当任何/全部都不存在时,您想抛出错误。您not
的代码中缺少 a 。
只是改变:
if any(Campionati_per_controllo_errori): # If any of them is present, throw an error. Not what we want.
return "FAILED (manca 1 campionato)"
至:
if not all(Campionati_per_controllo_errori): # If not all of them are present, throw an error.
return "FAILED (manca 1 campionato)"
推荐阅读
- python - Python - Pandas - 根据 updated_at 列创建列 valid_until
- c# - 在两个屏幕中最大化表单窗口C#
- bash - 我在这个 read while 循环中使用了什么 shell 范围?
- aws-lambda - Dynamo 数据库访问问题 AWS Lambda
- ocr - 真实视频字幕生成中使用拉伸阿拉伯字母的规则是什么?
- c# - C#方法调用多次
- macos - 安装 PHP 7.1 for Mac 时出错(使用 Homebrew)
- sql - 如何捕获基于 Web 的应用程序发送到 Oracle 服务器的 SQL 查询?
- mysql - SQL 中的正则表达式性能
- python - 返回 UnboundLocalError 的 Zip() 函数:分配前引用的局部变量 'zip'