python异步IO任务未并行执行
我正在创建异步任务,以便它们可以像这样并行执行python异步IO任务未并行执行,python,python-3.x,asynchronous,async-await,Python,Python 3.x,Asynchronous,Async Await,我正在创建异步任务,以便它们可以像这样并行执行 for symbol in config.symbol_list: tasks.append(asyncio.ensure_future(get_today_Data_async(symbol), loop=loop)) loop.run_until_complete(asyncio.wait(tasks)) 这是我想并行执行的任务 async def get_today_
for symbol in config.symbol_list:
tasks.append(asyncio.ensure_future(get_today_Data_async(symbol), loop=loop))
loop.run_until_complete(asyncio.wait(tasks))
这是我想并行执行的任务
async def get_today_Data_async(symbol):
periodType = 'day'
period = 1
frequencyType = 'minute'
frequency = '1'
use_last10_Min = False
logging.info(f'Updating data {symbol} started...')
try:
logging.info(f'thread id - {threading.get_ident()} getting market data {symbol} periodType {periodType} period {period} frequencyType {frequencyType} frequency {frequency}')
est = pytz.timezone('US/Eastern')
if use_last10_Min:
startDate = (datetime.datetime.now()- datetime.timedelta(minutes=10)).astimezone(tz=est).timestamp()
else:
startDate =(datetime.datetime.now().replace(hour=0, minute=0, second=0, microsecond=0)).astimezone(tz=est).timestamp()
endDate = (datetime.datetime.now()+datetime.timedelta(hours=48)).astimezone(tz=est).timestamp()
endDate = str(endDate).split('.')[0] + '000'
startDate = str(startDate).split('.')[0] + '000'
reqDict = {'apikey': '' + config.client_id + '@AMER.OAUTHAP','endDate': endDate, 'frequencyType': frequencyType,'frequency': frequency,
'startDate': startDate, 'needExtendedHoursData': usePreMarket}
header = {'Authorization': 'Bearer ' + config.token['access_token'] + '', 'content-type': 'application/json'}
logging.info(f"thread id - {threading.get_ident()} datetime check {symbol} {datetime.datetime.now()} {reqDict}")
with await tlock:
resp = requests.get("https://api.tdameritrade.com/v1/marketdata/" + symbol + "/pricehistory", params=reqDict)
logging.info(f'thread id - {threading.get_ident()} datetime check {symbol} {datetime.datetime.now()} {resp.status_code}')
if resp.status_code == 200 and not resp.json()['empty']:
candles = resp.json()['candles']
logging.info(f"symbol candel {symbol} {frequencyType} {frequency} {period} {get_one_hour(resp.json()['candles'])}")
if not usePreMarket:
newcandles = []
EST = pytz.timezone('us/eastern')
time_ist_end = datetime.datetime.now(EST).replace(hour=16, minute=00, second=00)
time_ist_start = time_ist_end.replace(hour=9, minute=30, second=00)
for x in candles:
tmp_date = datetime.datetime.fromtimestamp((x.get('datetime') / 1000), tz=pytz.timezone('US/Eastern'))
if tmp_date > time_ist_start and tmp_date < time_ist_end:
newcandles.append(x)
if len(newcandles) > 0:
process_price(symbol,newcandles)
else:
if len(candles) > 0:
process_price(symbol, candles)
logging.info(f" symbol - {symbol} status code {resp.status_code} resp {resp.text}")
except Exception as e:
traceback.print_exc()
logging.error(f'Error in getting price {e}')
logging.info(f'Updating data {symbol} completed...')
这意味着任务是按顺序执行的。大约有500个符号。你能帮我一下吗,这样我就可以并行执行任务了在python中,理论上任何给定的时间都没有并行执行。
async def get_today_Data_async(symbol):
periodType = 'day'
period = 1
frequencyType = 'minute'
frequency = '1'
use_last10_Min = False
logging.info(f'Updating data {symbol} started...')
try:
logging.info(f'thread id - {threading.get_ident()} getting market data {symbol} periodType {periodType} period {period} frequencyType {frequencyType} frequency {frequency}')
est = pytz.timezone('US/Eastern')
if use_last10_Min:
startDate = (datetime.datetime.now()- datetime.timedelta(minutes=10)).astimezone(tz=est).timestamp()
else:
startDate =(datetime.datetime.now().replace(hour=0, minute=0, second=0, microsecond=0)).astimezone(tz=est).timestamp()
endDate = (datetime.datetime.now()+datetime.timedelta(hours=48)).astimezone(tz=est).timestamp()
endDate = str(endDate).split('.')[0] + '000'
startDate = str(startDate).split('.')[0] + '000'
reqDict = {'apikey': '' + config.client_id + '@AMER.OAUTHAP','endDate': endDate, 'frequencyType': frequencyType,'frequency': frequency,
'startDate': startDate, 'needExtendedHoursData': usePreMarket}
header = {'Authorization': 'Bearer ' + config.token['access_token'] + '', 'content-type': 'application/json'}
logging.info(f"thread id - {threading.get_ident()} datetime check {symbol} {datetime.datetime.now()} {reqDict}")
with await tlock:
resp = requests.get("https://api.tdameritrade.com/v1/marketdata/" + symbol + "/pricehistory", params=reqDict)
logging.info(f'thread id - {threading.get_ident()} datetime check {symbol} {datetime.datetime.now()} {resp.status_code}')
if resp.status_code == 200 and not resp.json()['empty']:
candles = resp.json()['candles']
logging.info(f"symbol candel {symbol} {frequencyType} {frequency} {period} {get_one_hour(resp.json()['candles'])}")
if not usePreMarket:
newcandles = []
EST = pytz.timezone('us/eastern')
time_ist_end = datetime.datetime.now(EST).replace(hour=16, minute=00, second=00)
time_ist_start = time_ist_end.replace(hour=9, minute=30, second=00)
for x in candles:
tmp_date = datetime.datetime.fromtimestamp((x.get('datetime') / 1000), tz=pytz.timezone('US/Eastern'))
if tmp_date > time_ist_start and tmp_date < time_ist_end:
newcandles.append(x)
if len(newcandles) > 0:
process_price(symbol,newcandles)
else:
if len(candles) > 0:
process_price(symbol, candles)
logging.info(f" symbol - {symbol} status code {resp.status_code} resp {resp.text}")
except Exception as e:
traceback.print_exc()
logging.error(f'Error in getting price {e}')
logging.info(f'Updating data {symbol} completed...')
Python的全局解释器锁(GIL)是一种复杂的机制,我在这里不作解释,如果您愿意,可以阅读它,但它阻止Python代码同时在两个不同的线程中运行
那么为什么仍然使用线程/并行处理呢?
在Python中,解决I/O(输入输出)问题是一个典型的适合并行处理的方法,我用一个例子解释。
如果您有一个发出HTTP请求的代码,因为网络数据传输比cpu处理慢得多,为了使代码效率最高,您宁愿在一个线程发出请求,而不是让程序卡住并等待响应,继续用其他线程发出请求,而不是每次返回响应,注意从该响应中获得的输出
这就是为什么在Python中,许多问题可能不应该是多线程的,而在其他语言中它有一些好处
使用python实现真正并行处理的一种方法是使用
多处理
模块。但请记住,它将比普通python执行有更多的RAM使用,因为内存中有多个相同的堆栈,并且它不一定会更快,因为打开和关闭进程需要时间。在python中,理论上任何给定时间都没有并行执行。
Python的全局解释器锁(GIL)是一种复杂的机制,我在这里不作解释,如果您愿意,可以阅读它,但它阻止Python代码同时在两个不同的线程中运行
那么为什么仍然使用线程/并行处理呢?
在Python中,解决I/O(输入输出)问题是一个典型的适合并行处理的方法,我用一个例子解释。
如果您有一个发出HTTP请求的代码,因为网络数据传输比cpu处理慢得多,为了使代码效率最高,您宁愿在一个线程发出请求,而不是让程序卡住并等待响应,继续用其他线程发出请求,而不是每次返回响应,注意从该响应中获得的输出
这就是为什么在Python中,许多问题可能不应该是多线程的,而在其他语言中它有一些好处
使用python实现真正并行处理的一种方法是使用多处理
模块。但请记住,它将比正常的python执行有更多的RAM使用,因为内存中有多个相同的堆栈,而且它不一定会更快,因为打开和关闭进程需要时间