如何用循环将多客户广告数据合并为单个DataFrame?
问题描述
我有一个包含客户ID的列表:
clients = ['act_1078577379193828', 'act_1503882476478990', 'act_232830897389702']
我通过Python循环执行异步任务,获取每个客户的广告活动数据:
for advertiser in clients: async_job = AdAccount(advertiser).get_insights(fields=fields, params=params, is_async=True) async_job.api_get() while async_job[AdReportRun.Field.async_status]!= 'Job Completed': time.sleep(1) async_job.api_get() time.sleep(1) df = pd.DataFrame(async_job.get_result())
但当前代码每次循环都会覆盖df,最终只能得到最后一个客户的数据。我曾用if-elif逐个创建DataFrame:
for advertiser in clients: async_job = AdAccount(advertiser).get_insights(fields=fields, params=params, is_async=True) async_job.api_get() while async_job[AdReportRun.Field.async_status]!= 'Job Completed': time.sleep(1) async_job.api_get() time.sleep(1) if advertiser == 'act_1078577379193828': df1 = pd.DataFrame(async_job.get_result()) elif advertiser == 'act_1503882476478990': df2 = pd.DataFrame(async_job.get_result()) elif advertiser == 'act_232830897389702': df3 = pd.DataFrame(async_job.get_result())
但后续客户ID会超过44个,这种方式完全不可行。求一种无需大量分支判断,就能将所有客户数据合并到单个DataFrame的方法。
*注:async_job.get_result()是数据返回的位置,其输出示例如下:
[<AdsInsights> { "account_id": "232830897389702", "account_name": "Advertiser_Account_Name", "actions": [ { "action_type": "link_click", "value": "4" }, { "action_type": "post_engagement", "value": "4" }, { "action_type": "page_engagement", "value": "4" } ], "ad_name": "***", "adset_name": "***", "campaign_name": "***", "clicks": "15", "cpc": "0.568", "cpm": "15.160142", "ctr": "2.669039", "date_start": "2022-08-26", "date_stop": "2022-08-26", "frequency": "1.05838", "impressions": "562", "inline_post_engagement": "4", "objective": "LEAD_GENERATION", "reach": "531", "spend": "8.52" },
解决方案
可以通过列表存储单个客户DataFrame,最后合并的方式实现,完全不需要分支判断,代码简洁且易于扩展:
优化后代码
import pandas as pd import time # 假设AdAccount、AdReportRun已提前导入 clients = ['act_1078577379193828', 'act_1503882476478990', 'act_232830897389702'] # 初始化空列表,用于存放每个客户的DataFrame df_list = [] for advertiser in clients: # 执行异步任务并等待完成 async_job = AdAccount(advertiser).get_insights(fields=fields, params=params, is_async=True) async_job.api_get() while async_job[AdReportRun.Field.async_status] != 'Job Completed': time.sleep(1) async_job.api_get() time.sleep(1) # 将当前客户的数据转为DataFrame,添加到列表中 current_df = pd.DataFrame(async_job.get_result()) df_list.append(current_df) # 合并所有客户的DataFrame final_df = pd.concat(df_list, ignore_index=True)
关键步骤说明
- 初始化空列表:
df_list用来临时存储每个客户的DataFrame,避免变量覆盖或大量命名变量的问题。 - 循环添加DataFrame:每次处理完一个客户,就把生成的DataFrame追加到列表中。
- 合并所有数据:用
pd.concat()将列表中的所有DataFrame纵向合并,ignore_index=True重置合并后的索引,避免索引重复。
可选优化
如果担心某个客户返回空数据导致合并失败,可以在添加前做判断:
current_df = pd.DataFrame(async_job.get_result()) if not current_df.empty: df_list.append(current_df)
内容的提问来源于stack exchange,提问作者André Filho
相关产品推荐
相关产品推荐

