Unity模拟自动驾驶方向盘角度预测

Unity模拟器是一款模拟汽车行驶的赛车游戏。这个模拟器是一个可以收集游戏中数据图片,以及游戏中你控制赛车的角度。

1数据介绍

游戏中模拟了赛车上安装左中右三个摄像头,数据就是这些摄像头截取的画面。

模拟器关于方向盘的角度只有中间摄像头对应的转动角度。

实现

1对图像进行水平翻 有扩充数据的效果

def horizontal_filp(img, degree):
    '''

    :param img:
    :param degree:
    :return:
    cv2.flip 值为1代表水平翻转 翻转之后角度正负变反
    '''
    choice = np.random.choice([0,1])
    if choice == 1:
        img, degree = cv2.flip(img, 1), -degree
    return (img, degree)

2随机调成图片的亮度

def randonm_brightness(img, degree):
    '''
    随机调整输入图像的亮度 调整强度于 0.1(变黑)和1(无变化)之间
    :param img:
    :param degree:
    :return:
    '''
    hsv = cv2.cvtColor(img, cv2.COLOR_BGR2HSV)
    #调整亮度V: alpha×V
    alpha = np.random.uniform(low=0.1, high=1, size=None)
    v = hsv[:, :, 2]
    v = v * alpha
    hsv[:, :, 2] = v.astype('uint8')
    rgb = cv2.cvtColor(hsv.astype('uint8'), cv2.COLOR_HSV2RGB)

    return (rgb, degree)

3左右摄像头角度的转换

def left_right_random_swap(img_address, degree, degree_corr=1.0/4):
    '''
    随机从左, 中, 右图像中选择一张图像, 并相应的调整转动的角度。
    :param img_address: 中间图像的文件路径
    :param degree: 中间图像对于方向盘转动角度
    :param degree_corr: 左中右关系的值
    :return:
    '''
    swap = np.random.choice(['L', 'R', 'C'])

    if swap == 'L':
        img_address = img_address.replace('center', 'left')
        corrected_label = np.arctan(math.tan(degree)+degree_corr)
        return (img_address, corrected_label)

    elif swap == 'R':
        img_address = img_address.replace('center', 'right')
        corrected_label = np.arctan(math.tan(degree) - degree_corr)
        return (img_address, corrected_label)

    else:
        return (img_address, degree)

4数据平衡 以一定概率丢弃角度为0的图片

def discard_zero_steering(degrees, rate):
    '''
    以一定概率丢弃转动角度为0的数据
    :param degrees: 转动角度的list
    :param rate: 丢弃系数 若 = 0.8 则80%保丢
    :return:
    '''
    steering_zero_idx = np.where(degrees == 0)
    steering_zero_idx = steering_zero_idx[0]
    size_del = int(len(steering_zero_idx)*rate)

    return  np.random.choice(steering_zero_idx, size=size_del, replace=False)

5网络结构的实现

def get_model(shape):
    '''
    预测方向盘角度: 以图像为输入, 预测方向盘的转动角度
    shape: 输入图像的尺寸, 例如(128, 128, 3)
    '''

    model = Sequential()
    
    model.add(Conv2D(8, (5, 5), strides=(1, 1), padding="valid", activation='relu', input_shape=shape))
    model.add(MaxPooling2D(pool_size=(2,2)))
    model.add(Dropout(0.5))

    model.add(Conv2D(16, (4, 4), strides=(1, 1), padding="valid", activation='relu', kernel_regularizer=l2(0.01), activity_regularizer=l1(0.01)))
    model.add(MaxPooling2D(pool_size=(2, 2)))
    model.add(Dropout(0.5))

    model.add(Conv2D(16, (4, 4), strides=(1, 1), padding="valid", activation='relu', kernel_regularizer=l2(0.01), activity_regularizer=l1(0.01)))
    model.add(MaxPooling2D(pool_size=(2, 2)))
    model.add(Dropout(0.5))

    model.add(Conv2D(16, (5, 5), strides=(1, 1), padding="valid", activation='relu', kernel_regularizer=l2(0.01), activity_regularizer=l1(0.01)))
    model.add(MaxPooling2D(pool_size=(2, 2)))
    model.add(Dropout(0.5))
    model.add(Flatten())
    
    model.add(Dense(128, activation='relu'))
    model.add(Dropout(0.5))
    model.add(Dense(50, activation='relu'))
    model.add(Dropout(0.5))
    model.add(Dense(10, activation='relu'))
    model.add(Dropout(0.5))
    model.add(Dense(1, activation='linear'))

    sgd = SGD(lr=0.01)
    adm=Adamax(lr=0.02, beta_1=0.9, beta_2=0.999)
    model.compile(optimizer=sgd, loss='mean_squared_error')
    return model

6截取了图片的部分图片并对我们的图片进行归一化操作

 X[example,:,:,:] = cv2.resize(img[80:140, 0:320], (shape[0], shape[1]) ) / 255 - 0.5

7训练结果

posted @ 2019-12-10 03:32  朱小丰的丰  阅读(784)  评论(0编辑  收藏  举报