2017-08-30 71 views
0

我有2个线程正在侦听的,可以进来任何时候2条不同的UART数据线设置事件。我也有一个只是一个计时器的第三个线程。在我的主线程,我想等待所有这三个线程以触发解析数据和更新型函数信号。的Python:从多个线程

正在使用1个事件,每个线程在设置事件之前都会设置一个单独的标志,以指示哪一个事件触发了事件可接受的解决方案,还是有更好的方法可以做到这一点?

使用Python 2.7

例如:

''' 
UART RX thread for GNSS 
''' 
def uart_rx_gnss(threadName, ser): 
    global event_flag 
    global rx_buffer 

    while(1): 
    line = ser.readline() 
    logger.debug(" GNSS >> " + str(line)) 

    with t_lock: 
     rx_buffer = line 
     event_flag = EVENT_GNSS 
     t_event.set()  

''' 
UART RX thread for cc1350 
''' 
def uart_rx_cc1350(threadName, ser, t_lock, t_event): 
    global event_flag 
    global rx_buffer 

    while(1): 
    cc1350_buffer = ser.readline() 
    logger.debug(" CC1350 >> " + str(cc1350_buffer)) 

    with t_lock: 
     rx_buffer = line 
     event_flag = EVENT_CC1350 
     t_event.set() 


''' 
    Periodically update if no uart 
''' 
def periodic_update(threadName, t_lock, t_event): 
    global event_flag 

    while(1): 
    time.sleep(3) 
    with t_lock: 
     event_flag = EVENT_TIMEOUT 
     t_event.set() 

''' 
Main 
''' 
def main(verbosity="info", mode="normal"): 
    # SIGING Handler 
    signal.signal(signal.SIGINT, signal_handler) 

    ######### GLOBAL VARIABLES ######### 
    global event_flag 

    ser = ic.initialize_uart('/dev/ttymxc6', 9600) 
    thread.start_new_thread(uart_rx_gnss, ("Thread-GNSS-RX", ser)) 

    ser = ic.initialize_uart('/dev/ttymxc4') 
    thread.start_new_thread(uart_rx_cc1350, ("Thread-cc1350-RX", ser, lock, event)) 

    thread.start_new_thread(periodic_update, ("Updater", lock, event)) 

    # Main Loop 
    while (running == True): 
    event.wait() 

    if (event_flag == EVENT_TIMEOUT): 
     logger.info("EVENT: TIMEOUT") 
     # UPDATE 
    elif (event_flag == EVENT_GNSS): 
     logger.info("EVENT: GNSS") 
     # Parse rx_buffer 
    elif (event_flag == EVENT_CC1350): 
     logger.info("EVENT: CC1350") 
     # Parse rx_buffer 
    else: 
     logger.info("EVENT UNKNOWN") 

    event_flag = 0 
    event.clear() 

回答

0

这就会爆炸。

所有你需要的是两个关闭事件,并且你的全球evetn_flag将在比赛条件下被覆盖。

您应该使用该队列。

https://docs.python.org/3/library/queue.html

队列将保持秩序,并保证你的主线程将处理后的所有事件。

您可以将任意数据结构发布到队列 - 因此,由于yu alredy具有事件类型“quasi-enumeration”,因此您可以将此event_type作为第一个元素发布一个元组,并且无论您需要交换什么数据跨线程作为第二个元素。在产生线程之前只需创建一个queue.Queue对象,您甚至可以将其设置为全局变量,并使用队列的get方法而不是event.wait()

+0

感谢这听起来像一个更好的解决方案。话虽这么说,不会锁防止你所描述的竞争条件? –