zoukankan      html  css  js  c++  java
  • 2020中国高校计算机大赛 华为云大数据挑战赛--热身赛--赛题分析、数据理解

    一、赛题理解  

      本次比赛任务是利用历史数据并结合地图信息

      预测五和张衡交叉路口  未来一周  周一(2019年2月11日)和周四(2019年2月14日)两天  的5:00-21:00通过wuhe_zhangheng路口4个方向的车流量总和。

      要求模型输出格式如下:   

              {"data":{"resp_data":{"wuhe_zhangheng":[1,4,5,6,4...]}}}

      从5:00开始每5min的预测数据,第一个数据为5:00-5:05的流量值,最后一个数据为20:55-21:00。

      两天的数据按时间先后放在一起,总共有384个数据。

      

      预测输入形式:输入需要预测的日期,按照赛题,输入 {"req_data":["2019-2-11,2019-2-14"]}          

      预测数据形式一条道路,一天,四个方向总和,每五分钟预测一次,一天就有60 * 24 / 5 = 288 条记录,输出5:00 - 21:00这16个小时的数据,便是288/24 * 16 = 192 条数据

             预测一天输出结果为 1 * 192 ,两天便是 1 * (192 * 2 )=  1 * 384

      注意点预测的是一周中两天的数据,并且这两天都是独立的,没有前后数据,这意味着很难用基于时间顺序流进行预测(需要输入预测值之前一段时间的数据)。

          之前看很多交通预测论文,预测未来数据时,会将连续历史信息作为默认信息

          比如预测T时段的信息,那么T-1、T-2、T-3 ……等前段的数据都是已知的,并且是作为输入送到模型的。

          交通预测理论分析,和物理实验一样,做了很多假设,面对现实,未免会有误差。(同时也说明我的能力太菜了……这个问题应该是可以通过对模型构建来解决,但是我想了几天,脑阔疼)

    二、原始数据分析

      官方数据:  4周(2019.1.12 – 2019.2.8)深圳龙岗区坂田街道交通流量历史数据 

      数据形式:

        

      

      其中,time为上述格式时间字符串,cross为路口名,direction为车流起始方向,leftFlow是左转车流,straightFlow是直行车流。

      说明

      (1) 十字路口包含四个方向车流数据,此处未全部列出。

      (2) 路口名称分别为:五和路、张衡路、稼先路、隆平路、冲之大道。可以通过但不限于百度地图等地图软件获取地图路网信息。

      (3) 因为右转车流不受信号灯控制,因此未做统计。

     

      数据理解:

        官方说明给出了五个路口,但是实际上有一条冲之-贝尔路口没有说明。

        这些路口分别为:冲之-贝尔路口、冲之-稼先路口、冲之-隆平路口、五和-稼先路口、五和-隆平路口、五和-张衡路口这六条。

        其中四条路口为十字路口、两条路口为三叉路口。所以每一天都会有4*4 + 2*3 = 22个方向的数据,每个方向记录每隔五分钟的交通流,为288条数据。

        官方给出4周,也就是 4 * 7 = 28 天,【28,22,288】

    三、官方baseline 数据处理

        数据处理方式一般是需要根据模型来变动。

        官方baseline是根据梯度提升决策树进行预测,可以看作是回归模型,根据输入特征值{Xi : i = 1,2,3,……n},获得回归结果(Y)

        baseline只使用了五和-张衡路口的数据,【28,4,288】 = 32256,但是真实提取数据只有29036条数据,说明28天的数据中存在缺失。(若使用时间顺序预测,那么需要补充这部分数据)

        baseline从每一天的日期中,提取出了两个特征,X1 = 星期/6(X1为一个数值,取值范围是【0,1,2,3,4,5,6】/ 6 = 【0,0.167,0.333,0.5,0.667,0.833,1】)

                               X2 = 每5分钟的时刻  【0,5,10,15,……,23*60 + 55】/(24*60) (【1*288】)

                        预测目标:Y = number   【1*288】

        baseline的模型输入:( X1 , X2(i))输出:Y(i)

        所以官方baseline数据处理主要就是通过原始数据生成这两个特征。

        首先,读取原始数据,将五和-张衡路口数据中时间和交通流全部提取,大小为【29036,2】      

    def read_file(path, filename):
        calfile = os.path.join(path, filename)
        original = pd.read_csv(calfile, header=None)
        data = pd.DataFrame(columns=["time", "number"])
        data["time"] = original[0]
        data["number"] = original[3] + original[4]
        return data
        
    # read data of one day
    def read_data_day(path, date):
        day_data = pd.DataFrame(columns=["time","number"])
        caldir = os.path.join(path, date)
        # read data of one day
        for f in os.listdir(caldir):
            if re.match(r'wuhe_zhangheng.*.csv', f):
                day_data = day_data.append(read_file(caldir, f), ignore_index=True)
        return day_data
    

        随后,将提取出的数据针对时间进行编码,得到两个特征分别对应星期和时刻。并将所有相同特征的数值取平均值。

        注意点:虽然是有四个星期的内容,但是baseline并没有针对第几个星期进行处理。所以不管是第一个星期一,还是第四个星期一,星期编码都是0。

             时刻也是一样。第一个星期一00:05时刻 与 第四个星期一00:05时刻,他们的X1, X2(i)编码是完全相同的。

             同时,五和-张衡路口时十字路口,每个时刻会记录四个不同方向的数据。

             所以对于每个X1、X2(i)会有16 条数据 (四个方向、四个星期),然后将这16个数据平均,变为一个输入

        缺失数据分析:

            上文提到,如果数据完整那么存在28 * 4 * 288 = 32256 条数据。

            按照时刻和星期进行分组,组成【288,7,16】的矩阵,每个元素代表某一个时刻,四个星期的所有方向数据集(总共4周,4个方向,于是有16个数据)

            所以数据应为【288,7,16】。每一个时刻,包含的数据总数应该为【16,16,16,16,16,16,16】

            但是,分析大赛给出数据中有三种形式,分别为

            【12,12,16,16,16,16,16】 前57个时刻

            【12,12,16,16,16,16,12】共223个时刻

            【12,13,16,16,16,16,12】 共8个时刻

            验证:57*(104)+ 223 * (100)+ 8*(101)= 29036 。

            通过缺失数据可以分析,数据量为12个星期,可能说明有一天没有五和-张衡路的数据(一天四个方向数据),或是某几天的数据中缺少五和-张衡路其中一个方向的                                数据。数据量为13则是某几天的数据缺失一个方向的记录。

                

    def get_data(path):
        raw_data = pd.DataFrame(columns=["time", "number"])
        for day in os.listdir(path):
            raw_data = raw_data.append(read_data_day(path, day))
        # encode time in raw data to weekday and timeindex(the n minutes of the day)
        df_dt = to_datetime(raw_data.loc[:, "time"], format="%Y/%m/%d %H:%M:%S")
        all_data = pd.DataFrame({
            "weekday": df_dt.dt.weekday/6.0,
            "timeindex": (df_dt.dt.hour * 60 + df_dt.dt.minute)/(24*60.0),
            "number": raw_data["number"].astype(int)}) 
        all_data = all_data.groupby(["weekday", "timeindex"]).sum().reset_index(level = ["weekday", "timeindex"])
            
        return all_data
    

      模型训练:

        baseline直接引用sklearn中的梯度提升决策树回归GradientBoostingRegressor进行预测。(没了解过,只知道决策树……基础要补课啊 )

      

    def train_model():
        X_train, X_test, y_train, y_test = train_test_split(local_data[['weekday','timeindex']], local_data['number'], 
                                                            test_size=0.1, random_state=42)
        print("X_train shape is: " + str(X_train.shape))
        print("X_test shape is: " + str(X_test.shape))
        
        params = {'n_estimators': 500, 'max_depth': 4, 'min_samples_split': 2,   #最优
                  'learning_rate': 0.01, 'loss': 'ls'}
        clf = GradientBoostingRegressor(**params)
        clf.fit(X_train, y_train)
        joblib.dump(clf, LOCAL_MODEL_PATH) #模型保存
    
        y_predict = clf.predict(X_test)  
        
        mse = mean_squared_error(y_test, y_predict)
        print("MSE: %.4f" % mse)
    

      

        

     

  • 相关阅读:
    unity3d优化-代码篇(不定期更新)
    Activity的生命周期
    继承了AppCompatActivity的全屏设置
    shaderlab UV动画所需的变量声明
    加载Assetbundle需要注意的地方
    VisualStudio中的编辑后期生成事件
    unity3D射线检测敌人是否在前方
    Unity3D 定时发射子弹
    Unity3D使用NGUI做个弹窗
    Unity3D TouchScript 插件教程一
  • 原文地址:https://www.cnblogs.com/xieviki650/p/12933949.html
Copyright © 2011-2022 走看看