예제 #1
0
        /// <summary>
        /// Load trees from dump files
        /// </summary>
        public override int LoadClassifier()
        {
            string treesRoot  = ConfigReader.Read("TreesRoot");
            int    bucketSize = int.Parse(ConfigReader.Read("BucketSize"));

            string treesDir = treesRoot ?? (Environment.CurrentDirectory + "\\batches");

            if (!Directory.Exists(treesDir))
            {
                Logger.Log("directory " + treesDir + " doesn't exists");
                return(0);
            }
            var dinfo = new DirectoryInfo(treesDir);

            _classifiers.Clear();

            var files = dinfo.GetFiles("*.dmp").OrderBy(f => f.Name).ToArray();

            if (bucketSize > 0)
            {
                files = files.Skip(bucketSize * _bucketNum).Take(bucketSize).ToArray();
                _bucketNum++;
            }
            int clid = 0;

            foreach (var finfo in files)
            {
                var cls = DecisionBatch.Load(finfo.FullName);
                _classifiers.Add(clid++, cls);
                Logger.Log(finfo.Name + " loaded;");
            }
            Logger.Log("all trees loaded;");
            return(clid);
        }
예제 #2
0
        /// <summary>
        /// build and test classifier
        /// </summary>
        public override ClassifierResult Build()
        {
            if (_trainLoader?.LearnRows == null)
            {
                throw new InvalidOperationException("train set is empty");
            }

            Clear();
            var ret = new ClassifierResult();

            using (var sw = new StreamWriter(new FileStream("auchist.csv", FileMode.Create, FileAccess.Write)))
            {
                sw.WriteLine("time;n;train auc;test auc;stype");

                // создаем первые классификаторы (first step)
                for (int i = 0; i < BatchesInFirstStep; i++)
                {
                    DecisionBatch cls;
                    if (IsLoadFirstStepBatches)
                    {
                        cls = DecisionBatch.Load(Environment.CurrentDirectory + "\\batches\\" + "batch_" + $"{i:0000.#}" + ".dmp");
                        if (cls == null)
                        {
                            cls = DecisionBatch.CreateBatch(_trainLoader.LearnRows, TreesInBatch, _nclasses, RfCoeff,
                                                            VarsCoeff, null, IsParallel, UseBatchLogit);
                            if (IsSaveTrees)
                            {
                                cls.Save();
                            }
                        }
                    }
                    else
                    {
                        cls = DecisionBatch.CreateBatch(_trainLoader.LearnRows, TreesInBatch, _nclasses, RfCoeff,
                                                        VarsCoeff, null, IsParallel, UseBatchLogit);
                        if (IsSaveTrees)
                        {
                            cls.Save();
                        }
                    }

                    // расчитываем метрики для тестового и обучающего множества (накопленные)
                    var testRes  = GetTestMetricsAccumulated(cls);
                    var trainRes = GetTrainMetricsAccumulated(cls);

                    Logger.Log("batch=" + i + " ok; train AUC=" + trainRes.AUC.ToString("F10") + " test AUC = " + testRes.AUC.ToString("F10"));
                    sw.WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + ";" + i + ";" + trainRes.AUC + ";" + testRes.AUC + ";none");
                    sw.Flush();

                    ret.AddStepResult(testRes, i);
                }

                // далее создаем классификаторы с учетом ошибки предыдущих (second step)
                int totalBatches = BatchesInFirstStep + BatchesInSecondStep;
                for (int i = BatchesInFirstStep; i < totalBatches; i++)
                {
                    DecisionBatch bestBatch = null;

                    // перестраиваем индексы плохо классифицированных объектов (плохие сначала)
                    RefreshIndexes();

                    double bestMetric = double.MaxValue;

                    // строим классификаторы и выбираем лучший
                    for (int k = 0; k < BatchesInBruteForce; k++)
                    {
                        var scls = DecisionBatch.CreateBatch(_trainLoader.LearnRows, TreesInBatch, _nclasses, RfCoeff,
                                                             VarsCoeff, _indexes, IsParallel, UseBatchLogit);

                        // расчитываем метрики для тестового множества
                        var trainCntRes = GetTrainClassificationCounts(scls);
                        int cnt         = UseBatchLogit ? 1 : scls.CountTreesInBatch;

                        var rlist = new RocItem[_trainResult.Count]; // массив для оценки результата
                                                                     // находим статистики классификации
                        int    idx    = 0;
                        double accerr = 0.0;
                        foreach (string id in _trainResult.Keys)
                        {
                            if (rlist[idx] == null)
                            {
                                rlist[idx] = new RocItem();
                            }

                            rlist[idx].Prob      = trainCntRes[id] / cnt; // среднее по наблюдениям
                            rlist[idx].Target    = _trainResult[id];
                            rlist[idx].Predicted = rlist[idx].Prob > 0.5 ? 1 : 0;

                            //accerr += Math.Pow(rlist[idx].Prob - rlist[idx].Target, 2);

                            idx++;
                        }

                        Array.Sort(rlist, (o1, o2) => (1 - o1.Prob).CompareTo(1 - o2.Prob));
                        var clsRes = ResultCalc.GetResult(rlist, 0.05);

                        accerr = clsRes.LogLoss;

                        Logger.Log("sub cls #" + k + " auc=" + clsRes.AUC.ToString("F10") + " eps=" + accerr + (accerr < bestMetric ? " [best]" : ""));

                        if (accerr < bestMetric)
                        {
                            bestMetric = accerr;
                            bestBatch  = scls;
                        }
                    }


                    var testRes  = GetTestMetricsAccumulated(bestBatch);
                    var trainRes = GetTrainMetricsAccumulated(bestBatch);
                    if (IsSaveTrees)
                    {
                        if (bestBatch != null)
                        {
                            bestBatch.Save();
                        }
                        else
                        {
                            Logger.Log("best Batch is null");
                        }
                    }

                    ret.AddStepResult(testRes, i);
                    Logger.Log("batch=" + i + " ok; train AUC=" + trainRes.AUC.ToString("F10") + "; test AUC = " + testRes.AUC.ToString("F10"));
                    sw.WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + ";" + i + ";" + trainRes.AUC + ";" + testRes.AUC + ";" + IndexSortOrder);
                    sw.Flush();
                }

                sw.Close();
            }

            return(ret);
        }