gpt4 book ai didi

python - 如何使用 pandas 中的 apply 函数实现此 iterrow 情况?

转载 作者:行者123 更新时间:2023-12-01 09:00:08 24 4
gpt4 key购买 nike

我有以下用于获取 IP 信息的代码:

import requests
import json
import pandas as pd
import swifter

def get_ip(ip):
response = requests.get ("http://ip-api.com/json/" + ip.rstrip())
geo = response.json()
location = {'lat': geo.get('lat', ''),
'lon': geo.get('lon', ''),
'region': geo.get('regionName', ''),
'city': geo.get('city', ''),
'org': geo.get('org', ''),
'country': geo.get('countryCode', ''),
'query': geo.get('query', '')
}
return(location)

为了将其应用到 IP 的整个数据帧 (df),我使用下一个:

df=pd.DataFrame(['85.56.19.4','188.85.165.103','81.61.223.131'])

for lab,row in df.iterrows():
dip = get_ip(df.iloc[lab][0])
try:
ip.append(dip["query"])
private.append('no')
country.append(dip["country"])
city.append(dip["city"])
region.append(dip["region"])
organization.append(dip["org"])
latitude.append(dip["lat"])
longitude.append(dip["lon"])
except:
ip.append(df.iloc[lab][0])
private.append("yes")

但是,由于 iterrows 非常慢并且我需要更高的性能,因此我想使用 swiftapply,它是 apply 函数的扩展。我用过这个:

def ip(x):
dip = get_ip(x)
if (dip['ip']=='private')==True:
ip.append(x)
private.append("yes")
else:
ip.append(dip["ip"])
private.append('no')
country.append(dip["country"])
city.append(dip["city"])
region.append(dip["region"])
organization.append(dip["org"])
latitude.append(dip["lat"])
longitude.append(dip["lon"])

df.swifter.apply(ip)

我收到以下错误:AttributeError:(“'Series'对象没有属性'rstrip'”,'发生在索引0')

我该如何解决这个问题?

最佳答案

rstrip 是字符串操作。为了将字符串操作应用于系列 Series,您必须首先在系列上调用 str 函数,该函数允许在 上执行矢量化字符串操作系列

具体来说,在代码中将 ip.rstrip() 更改为 ip.str.rstrip() 应该可以解决您的 AttributeError 问题。

经过一番研究后发现,您尝试执行的 requests.get 操作无法在 pandas 中进行矢量化(请参阅 Using Python Requests for several URLS in a dataframe )。我编写了以下内容,这应该比使用 iterrows 更有效一些。下面的操作是利用 np.vectorize 运行该函数来获取每个 IP 地址的信息。位置输入将保存为新 DataFrame 中的新列。

首先,我更改了您的 get_ip 函数以返回 location 字典,而不是 (location)

接下来,我使用 np.vectorize 创建了一个矢量化函数:

vec_func = np.vectorize(lambda url: get_ip(url))

最后,将 vec_func 应用于 df 以创建一个新的 DataFrame,将 dfvec_func 的位置输出合并code> 其中 df[0] 是包含您的网址的列:

new_df = pd.concat([df, pd.DataFrame(vec_func(df[0]), columns=["response"])["response"].apply(pd.Series)], axis=1)

上面的代码以字典的形式检索 DataFrame 中每一行的 API 响应,然后将字典映射到 DataFrame 中的列。最后你的新 DataFrame 看起来像这样:

                0      lat     lon     region      city             org country           query
0 85.56.19.4 37.3824 -5.9761 Andalusia Seville Orange Espana ES 85.56.19.4
1 188.85.165.103 41.6561 -0.8773 Aragon Zaragoza Vodafone Spain ES 188.85.165.103
2 81.61.223.131 40.3272 -3.7635 Madrid Leganés Vodafone Ono ES 81.61.223.131

希望这可以解决 InvalidSchema 错误,并为您带来比 iterrows() 更好的性能。

关于python - 如何使用 pandas 中的 apply 函数实现此 iterrow 情况?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52519675/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com