滴滴算法大賽算法解決過程 - 數據分析

題目分析

賽題詳情
構建一個模型,根據天氣,交通,區域裏面的各類設施,以往歷史數據,預測將來的某個時間點,某個區域裏,打車需求的缺口。整個算法其實就是一個有監督的機器學習的過程。php

數據整理

下載後的整個壓縮數據包575M,其中包括的訂單數據大約900萬條。(其餘Master表數據量很小,這裏忽略不計)
使用MongoDB存儲的話,大概使用2GB的空間,所有導入以後,工做用計算機十分卡頓。MongoCola管理軟件失去響應。因此,這裏的訂單按照日期導入。(訓練的時候,按照天來訓練)注意:官方的訂單數據的 訂單號 OrderID是主鍵重複的。這裏以第一次出現的訂單號的數據爲準。算法

因爲數據量很是龐大,因此這裏建議將中間的計算結果也放入數據庫中備用。
博客園不支持圖片放大功能,若是您想更好的查看圖片,也可使用如下網址得到更好的閱讀體驗:
http://codesnippet.info/Article/Index?ArticleId=00000038數據庫

訂單數據整理

訂單數據整理,主要是整理出各個時段,各個地域的訂單數據。機器學習

  • 時間段
  • 地域編號
  • 需求數
  • 缺口
  • 缺口比例

數據整理儘可能使用LINQ進行處理,MONGODB查詢是消耗時間的!!!,這裏數據庫只是用做數據的存儲不作計算函數

private void btnImportDB_Click(object sender, EventArgs e)
        {
            string rootFolder = txtRootDir.Text;
            //Order: Root + "\order_data"
            foreach (var filename in Directory.GetFiles(rootFolder + "\\order_data"))
            {
                if (!filename.Contains("._"))
                {
                    string strDate = filename.Substring(filename.LastIndexOf("_") + 1);
                    var colname = "Order_" + strDate;
                    Database.Clear(colname);
                    var orderlist = new List<Order>();
                    var read = new StreamReader(filename);
                    while (!read.EndOfStream)
                    {
                        var o = Order.Gernerate(read.ReadLine());
                        orderlist.Add(o);
                    }
                    orderlist = orderlist.Distinct(x => x.order_id).ToList();
                    Database.InsertRecBatch(orderlist, colname);


                    var orderGaplist = new List<OrderGap>();
                    Database.Clear("OrderGap_" + strDate);
                    for (int time = 1; time < 144 + 1; time++)
                    {
                        for (int area = 1; area < 66 + 1; area++)
                        {
                            var m = new OrderGap() {  DistrictId = area,TimeSlient = time};
                            m.Total = orderlist.Count((x) => { return x.DistrictID == area && x.TimeSlient == time; });  
                            m.Gap = orderlist.Count((x) => { return x.DistrictID == area && x.TimeSlient == time && x.driver_id == "NULL" ; });
                            m.GapPercent = m.Total == 0 ? 0 : Math.Round(((double)m.Gap / m.Total) * 100, 2);
                            orderGaplist.Add(m);
                        }
                    }
                    Database.InsertRecBatch(orderGaplist, "OrderGap_" + strDate);
                    //暫時只分析一天數據
                    break;
                }
            }
        }

利用Excel,可視化數據

如下是2016-01-01的數據分析。藍色的是GAP缺口數,紅色的是Total數。
一天24個小時總體需求分佈能夠看個大概了。
PS 區域1 :佔總體的5.1%訂單量,有必定的參考價值學習

PS 區域5 :佔總體的22.5%訂單量,有必定的參考價值
這裏看到,整個24小時分佈極不均衡。考慮到 01-01 是一個特殊的日子,你們爲了跨年而在零點以後選擇打車也是能夠理解的。
excel

一樣的51區域,2016-01-02的狀況則比較正常,總體的高峯出如今夜間16:50 - 17:20(評價訂單850) 左右。21:10,22:00也是兩個小高峯(平均訂單720)。code

擬合

Gap的預測,是創建在一個擬合函數上的。也有一些機器學習的味道。圖片

總的Gap函數 = 函數(時間,地區)ip

  • TimeID : 時間片編號
  • DistricID:地區編號
  • Traffic:交通流量
  • Weather:天氣
  • POI:設施數

百度地圖POI說明
注意:每家公司的POI分類都是不一樣的,這裏只是將百度POI作個例子,滴滴打車的POI和百度的POI定義好像是不一樣的。

交通流量和時間有關,一個地方的擁堵程度和時間有關係
不一樣的地區,各類設施配置不一樣。
天氣和時間有關。

Gap函數 = 函數(交通擁擠度函數(時間,地區編號),POI函數(地區編號),天氣函數(時間))

這裏能夠認爲,一個地方的打車人數,交通越堵,則打車的GAP越大。天氣很差,打車的人則越多,GAP也越大。設施越多的地方,打車的需求也越多,GAP可能也越大。可是這一切都只是可能性。
(題外話,其實真實的狀況也要考慮節假日的問題,在節假日的時候,GAP可能會變大。固然這是一我的文的考量了)

算法

交通擁堵函數:
這裏的交通擁堵函數是使用4個等級表示的。

  • LV1 20條路 權重8
  • LV2 10條路 權重4
  • LV3 15條路 權重2
  • LV4 05條路 權重1
    那麼擁堵指數怎麼計算呢?這裏應該是對每一個擁堵喲一個權重,等級越高,權重越大。
    擁擠度 = SUM(權重 * 數量)
    固然權重也是一個須要訓練和擬合的。
    (設施數和天氣差很少,也是一樣考慮的。)
    這裏有三個指標,每種指標對於總體的影響程度也是須要訓練的。

各項指標分析

起始區域差距

如下數據爲2016-01-01的數據統計

總體有效訂單數:498789(訂單ID去重複)
66個區域的訂單分佈是極其不均衡的.

MAX MIN AVG
112023 71 7557.4

排名後33位的,總共只有總體的4.37%的訂單
排名前5位的,總共只有總體的50.87%的訂單

起始區域POI總體數目和訂單數關係

咱們將POI總數/30 和訂單數一塊兒放到柱狀圖中發現,POI總數和訂單數應該有一些聯繫。
一個區域POI數越多說明這個地區越是繁華,從這裏打車的需求就越多。

任務

  • 研究同一時間片,同一地區,按照日期變化,數據的變化。觀察天氣對數據變化的影響
  • 研究同一時間片,不一樣地區,POI的數量對數據變化的影響
  • 研究每一個區域的需求量,可能每一個區域的需求量基準數值都是差很少的。
相關文章
相關標籤/搜索