Exemple #1
0
def make_ll_lc_event(vehicles, id2obj, meas, platooninfo, dt, addevent_list, lcevent_list):
    """Makes the lc_events for NewellLL model."""
    for veh in vehicles:
        curveh = id2obj[veh]
        leadinfo = helper.makeleadinfo([veh],platooninfo,meas)[0]
        t_nstar, t_n = platooninfo[veh][:2]
        for count, j in enumerate(leadinfo):
            curlead, start, end = j
            # make lc_event - supports single vehicle simulation only
            curlen = meas[curlead][0,6]
            if start > t_n or (t_n > t_nstar and count == 0):  # LC or merge
                prevlane, newlane = meas[veh][start-t_nstar-1, 7], meas[veh][start-t_nstar,7]
                if newlane != prevlane:  # veh = 'i' vehicle in LL notation
                    userelax = True
                    ip1 = False
                    x1veh, x2veh = meas[veh][start-t_nstar,4], meas[veh][start-t_nstar,5]
                    if x2veh == 0:  # handle edge case
                        # print('warning - follower missing for '+str(veh)+' change at time '+str(start))
                        userelax = False
                        x1, x2 = None, None
                    else:
                        x1t_nstar, x2t_nstar = platooninfo[x1veh][0], platooninfo[x2veh][0]
                        x1, x2 = meas[x1veh][start-x1t_nstar,2], meas[x2veh][start-x2t_nstar,2]
                else:
                    temp = meas[veh][start-t_nstar,4]
                    tempt_nstar = platooninfo[temp][0]
                    if meas[temp][start-1-tempt_nstar,7] != newlane:  # veh = 'i+1' in LL notation
                        userelax = True
                        ip1 = True
                        x1veh, x2veh = meas[veh][start-1-t_nstar,4], meas[veh][start-t_nstar,4]
                        x1t_nstar, x2t_nstar = platooninfo[x1veh][0], platooninfo[x2veh][0]
                        x1, x2 = meas[x1veh][start-x1t_nstar,2], meas[x2veh][start-x2t_nstar,2]
                    else:
                        userelax = False
                        x1, x2, ip1 = None, None, None
            else:
                userelax = False  # no relax
                x1, x2, ip1 = None, None, None

            leadstate = (x1, x2, ip1)
            curevent = (start, 'lc', curveh, curlead, curlen, userelax, leadstate)

            if count == 0:
                curevent = (start, 'add', curveh, curevent)
                addevent_list.append(curevent)
            else:
                lcevent_list.append(curevent)

    return addevent_list, lcevent_list
Exemple #2
0
def make_lc_event(vehicles, id2obj, meas, platooninfo, dt, addevent_list, lcevent_list):
    for veh in vehicles:
        curveh = id2obj[veh]
        leadinfo = helper.makeleadinfo([veh],platooninfo,meas)[0]
        for count, j in enumerate(leadinfo):
            curlead, start, end = j
            leadt_nstar = platooninfo[curlead][0]
            # even though the change occurs at time start, we want to calculate the relaxation using
            # the differences in headway at time start - 1. This leads to 4 combinations, first, whether
            # the new leader is simulated or not, and second, whether the new lead is available at start-1
            if curlead in vehicles:  # curlead is simulated (in the same calibration object)
                if start-1 < leadt_nstar:  # handle edge case where t_nstar = start
                    leadstate = (meas[curlead][0,2]-meas[curlead][0,3]*dt,
                                 meas[curlead][0,3])
                else:
                    leadstate = (None,)
                curlead, curlen = id2obj[curlead], None
            else:
                curlen = meas[curlead][0,6]  # curlead is already simulated, stored in curveh.leadstatemem
                if start-1 < leadt_nstar:  # handle edge case where t_nstar = start
                    leadstate = (meas[curlead][0,2]-meas[curlead][0,3]*dt,
                                 meas[curlead][0,3])
                else:
                    leadstate = (meas[curlead][start-1-leadt_nstar,2], meas[curlead][start-1-leadt_nstar,3])

            if count == 0:  # add event adds vehicle to simulation
                t_nstar, t_n = platooninfo[veh][0:2]
                if t_n > t_nstar:  # apply merger rule
                    userelax = True
                else:
                    userelax = False
                # make the add event
                curevent = (start, 'lc', curveh, curlead, curlen, userelax, leadstate)
                curevent = (start, 'add', curveh, curevent)
                addevent_list.append(curevent)
            else:  # lc event changes leader, applies relax
                curevent = (start, 'lc', curveh, curlead, curlen, True, leadstate)
                lcevent_list.append(curevent)

    return addevent_list, lcevent_list
Exemple #3
0
def make_dataset(meas, platooninfo, veh_list, rp=15, dt=.1):
    """Makes dataset from meas and platooninfo.

    Args:
        meas: see havsim.helper.makeplatooninfo
        platooninfo: see havsim.helper.makeplatooninfo
        veh_list: list of vehicle IDs to put into dataset
        dt: timestep
    Returns:
        ds: (reads as dataset) dictionary of vehicles, values are a dictionary with keys
            'IC' - (initial conditions) list of starting position/speed for vehicle
            'times' - list of two int times. First is the first time with an observed leader. Second is the
                last time with an observed leader +1. The number of times we call the model is equal to
                times[1] - times[0], which is the length of the lead measurements.
            'posmem' - (1d,) numpy array of observed positions for vehicle, 0 index corresponds to times[0].
                Typically this has a longer length than the lead posmem/speedmem.
            'speedmem' - (1d,) numpy array of observed speeds for vehicle
            'lead posmem' - (1d,) numpy array of positions for leaders, 0 index corresponds to times[0].
                length is subtracted from the lead position.
            'lead speedmem' - (1d,) numpy array of speeds for leaders.
            'lc times' - (1d,) numpy array with relaxation amounts at each time
        normalization amounts: tuple of
            maxheadway: max headway observed in training set
            maxspeed: max velocity observed in training set
            minacc: minimum acceleration observed in training set
            maxacc: maximum acceleration observed in training set

    """
    # get normalization for inputs, and get input data
    ds = {}
    maxheadway, maxspeed = 0, 0
    minacc, maxacc = 1e4, -1e4
    for veh in veh_list:
        # get data
        t0, t1, t2, t3 = platooninfo[veh][:4]
        leadpos, leadspeed = helper.get_lead_data(veh,
                                                  meas,
                                                  platooninfo,
                                                  dt=dt)
        # relaxation added
        relax = helper.get_fixed_relaxation(veh, meas, platooninfo, rp, dt=dt)
        leadpos = leadpos + relax
        # new input indicates lane change
        leadinfo = helper.makeleadinfo([veh], platooninfo, meas)
        rinfo = helper.makerinfo([veh],
                                 platooninfo,
                                 meas,
                                 leadinfo,
                                 mergertype=None)
        lc_input = np.zeros((t2 + 1 - t1, ))
        for lc in rinfo[0]:
            time, relax_amount = lc
            lc_input[time - t1] = relax_amount

        vehpos = meas[veh][t1 - t0:, 2]
        vehspd = meas[veh][t1 - t0:, 3]
        IC = [meas[veh][t1 - t0, 2], meas[veh][t1 - t0, 3]]
        headway = leadpos - vehpos[:t2 + 1 - t1]

        # normalization + add item to datset
        vehacc = [(vehpos[i + 2] - 2 * vehpos[i + 1] + vehpos[i]) / (dt**2)
                  for i in range(len(vehpos) - 2)]
        minacc, maxacc = min(minacc, min(vehacc)), max(maxacc, max(vehacc))
        maxheadway = max(max(headway), maxheadway)
        maxspeed = max(max(leadspeed), maxspeed)
        ds[veh] = {
            'IC': IC,
            'times': [t1, min(int(t2 + 1), t3)],
            'posmem': vehpos,
            'speedmem': vehspd,
            'lead posmem': leadpos,
            'lead speedmem': leadspeed,
            'lc times': lc_input
        }

    return ds, (maxheadway, maxspeed, minacc, maxacc)
Exemple #4
0
def make_calibration(vehicles, meas, platooninfo, dt, vehicle_class = None, calibration_class = None,
                     event_maker = None, lc_event_fun = None):
    """Sets up a Calibration object.

    Extracts the relevant quantities (e.g. LeadVehicle, initial conditions, loss) from the data
    and creates the add/lc event.

    Args:
        vehicles: list/set of vehicles to add to the Calibration
        meas: from havsim.calibration.algs.makeplatoonlist
        platooninfo: from havsim.calibration.algs.makeplatoonlist
        dt: timestep
        vehicle_class: subclassed Vehicle to use - if None defaults to CalibrationVehicle
        calibration_class: subclassed Calibration to use - if None defaults to Calibration
        event_maker: specify a function to create custom (lc) events
        lc_event_fun: specify function which handles custom lc events
    """
    # TODO - to make this consistent with deep_learning, y should be over the times t_n+1 - min(T_nm1+1, T_n)
    # and also this should use the helper function get_lead_data
    if vehicle_class is None:
        vehicle_class = CalibrationVehicle
    if calibration_class is None:
        calibration_class = Calibration
    if event_maker is None:
        event_maker = make_lc_event
    if lc_event_fun is None:
        lc_event_fun = lc_event

    # initialize
    vehicle_list = []
    addevent_list = []
    lcevent_list = []
    id2obj = {}
    if type(vehicles) == list:
        vehicles = set(vehicles)

    for veh in vehicles:
        # make lead memory - a list of position/speed tuples for any leaders which are not simulated
        leads = set(platooninfo[veh][4])
        needleads = leads.difference(vehicles)
        if len(needleads) > 0:
            leadstatemem = []
            leadinittime = None  # initial time lead is used
            leadinfo = helper.makeleadinfo([veh],platooninfo,meas)
            for j in leadinfo[0]:
                curlead, start, end = j
                if curlead in needleads:
                    if not leadinittime:
                        leadinittime = start
                    leadt_n = platooninfo[curlead][0]
                    poslist = list(meas[curlead][start-leadt_n:end-leadt_n+1,2])
                    spdlist = list(meas[curlead][start-leadt_n:end-leadt_n+1,3])
                    leadstatemem.extend(zip(poslist,spdlist))
                elif leadinittime is not None:
                    temp = [0]*(end-start+1)
                    leadstatemem.extend(temp)
        else:
            leadstatemem, leadinittime = None, None

        # get initial values, y for veh
        t_nstar, inittime, endtime = platooninfo[veh][0:3]
        initlead, initpos, initspd, length = meas[veh][inittime-t_nstar,[4,2,3,6]]
        y = meas[veh][inittime-t_nstar:endtime+1-t_nstar,2]

        # create vehicle object
        newveh = vehicle_class(veh, y, initpos, initspd, inittime, leadstatemem, leadinittime,
                                    length=length)
        vehicle_list.append(newveh)
        id2obj[veh] = newveh

    # create events
    addevent_list, lcevent_list = event_maker(vehicles, id2obj, meas, platooninfo, dt,
                                                addevent_list, lcevent_list)

    addevent_list.sort(key = lambda x: x[0], reverse = True)  # sort events in time
    lcevent_list.sort(key = lambda x: x[0], reverse = True)

    # make calibration object
    return calibration_class(vehicle_list, addevent_list, lcevent_list, dt, endtime=endtime,
                             lc_event_fun = lc_event_fun)
Exemple #5
0
def analyze_res_NN(res_list, meas, platooninfo, dt, mergeind = math.inf, times = 100, realistic = 1.1):
    out = {'mse':None, 'mse near LC':None, 'mse for merges':None, 'mse for many LC':None, 'realistic acc':None, 'short lc':None}

    mse = []
    nearlc = []
    merge = []
    manylc = []
    real = []
    out2 = []
    shortlc = []
    for count, item in enumerate(res_list.items()):
        veh, res = item

        leadinfo = helper.makeleadinfo([veh], platooninfo, meas)
        lctimes = [cur[1] for cur in leadinfo[0]]
        rinfo = helper.makerinfo([veh], platooninfo, meas, leadinfo)
        if len(lctimes) > len(rinfo[0]):  # this handles an edge case
            rinfo[0].insert(0, [None, -1])
        t_nstar, t_n, T_nm1 = platooninfo[veh][:3]
        if lctimes[0] == t_nstar:
            lctimes = lctimes[1:]

        curmeas = meas[veh][t_n-t_nstar:T_nm1+1-t_nstar,2]
        cursim = np.array(res['posmem'])
        curmse = np.mean(np.square(curmeas-cursim))/(3.28084**2)

        mse.append(curmse)
        if len(leadinfo[0]) > 3:
            manylc.append(curmse)  # many lc
        if count >= mergeind:
            merge.append(curmse)
        for count, curtime in enumerate(lctimes):
            curmse = np.square(cursim[curtime-t_n:curtime-t_n+times] - curmeas[curtime-t_n:curtime-t_n+times])
            curmse = np.sum(curmse)/len(curmse)/(3.28084**2)
            nearlc.append(curmse)  # near lc
            # try:
            curg = rinfo[0][count][1]
            if curg > 0:
                shortlc.append(curmse)
            # except:
            #     print('hello')

        simacc = [(cursim[i+2] - 2*cursim[i+1] + cursim[i])/(dt**2) for i in range(len(cursim)-2)]
        measacc = [(curmeas[i+2] - 2*curmeas[i+1] + curmeas[i])/(dt**2) for i in range(len(curmeas)-2)]
        upper = max(realistic*max(measacc), 4*3.28)
        lower = min(-6*3.28, realistic*min(measacc))
        temp1, temp2 = max(simacc), min(simacc)
        if temp1 < upper and temp2 > lower:
            real.append(1)
        else:
            real.append(0)
            out2.append(((upper, lower), (temp1, temp2)))

    out['mse'] = (np.mean(mse), np.median(mse), np.std(mse))
    out['mse near LC'] = (np.mean(nearlc), np.median(nearlc), np.std(nearlc))
    out['mse for merges'] = (np.mean(merge), np.median(merge), np.std(merge))
    out['mse for many LC'] = (np.mean(manylc), np.median(manylc), np.std(manylc))
    out['realistic acc'] = (np.mean(real))
    out['short lc'] = (np.mean(shortlc), np.median(shortlc), np.std(shortlc))
    print(out)
    return out, out2