У меня есть таблица с данными о погоде и количестве лесных пожаров в некоторые дни в некотором регионе:
Температура | Влажность | Скорость ветра | ... | Количество лесных пожаров
Все данные представлены в виде чисел.
Требуется по этим данным построить дерево решений, и, с помощью него и входных параметров (температура, влажность, скорость ветра, и т.д.) спрогнозировать количество лесных пожаров.
Для работы с деревьями решений в OpenCV есть класс CvDTree. Для построения дерева решений в данном классе есть метод train:
boolean train(Mat trainData, int tflag, Mat responses)
Как (каким образом и в каком порядке) преобразовать мои входные данные в Mat trainData?
Возможно, отвечающему поможет обсуждение по этой ссылке
Ответы
Ответ 1
Сделал небольшой пример (можно посмотреть тут https://github.com/NorsaG/OpenCVExample)
Некоторые мысли по задаче:
выбор инструмента (лично мое мнение - есть более удачные решения, тот
же xgboost или spark mllib)
выбор критерия (определять число -
задача сложная, а вот факт преодоления определённой границы нет)
Тестовые данные из головы, поэтому не сильно видны какие либо зависимости (даже очевидные для нас).
ненавижу нативные инструменты для java :) Кроме того, похожий код (с
минимальными исправлениями в виде имен классов) полностью отказался
работать на последней версии либы.
package org.firerate;
import org.opencv.core.Core;
import org.opencv.core.CvType;
import org.opencv.core.Mat;
import org.opencv.ml.CvRTParams;
import org.opencv.ml.CvRTrees;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.List;
public class FireRateExample {
static {
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
}
private static final int[] OFFSETS = {0, 5, 9}; // границы чисел. будем проверять и прогнозировать эти ситуации
public static void main(String[] args) throws IOException {
// загружаем данные
List csv = loadFile("fire_test.txt");
CvRTrees tree;
// настройка параметров. с этим можно долго и упорно играться, подгоняя так или иначе под модель
CvRTParams params = new CvRTParams();
params.set_max_depth(2);
Mat trainData;
Mat labels;
// строим модель для ситуаций: кол-во пожаров > 0, > 5 и > 9
for (int offset : OFFSETS) {
tree = new CvRTrees();
// создаем матрицу тренировочных данных размерности: х-1 чтобы отбросит
названия колонок, 3 - количество критериев (CvType.CV_32F - тип данных)
trainData = new Mat(csv.size() - 1, 3, CvType.CV_32F);
// классификатор -> 0 или 1 (в нашем случае - количество пожаров больше определенного значения? проставляться будет позднее)
labels = new Mat(csv.size() - 1, 1, CvType.CV_32S);
// загружаем построчно данные и проставляем их в матрицы
for (int i = 1; i < csv.size(); i++) {
String line = csv.get(i);
String[] str = line.split(",");
trainData.put(i - 1, 0, new float[]{Float.valueOf(str[0]), Float.valueOf(str[1]), Float.valueOf(str[2])});
labels.put(i - 1, 0, new int[]{Integer.valueOf(str[3]) > offset ? 1 : 0});
}
// тренируем и тестируем модель
// 1-й параметр: входная модель без класса
// 2-й параметр: тип входных данных (колонки(0) или строки(1))
// 3-й параметр: значения для входных данных
// tree.train(trainData, 1, labels);
// 8-й параметр: параметры дерева
tree.train(trainData, 1, labels, new Mat(), new Mat(), new Mat(), new Mat(), params);
testModel(tree, offset);
}
}
private static List loadFile(String fileName) throws IOException {
return Files.readAllLines(Paths.get(fileName));
}
private static void testModel(CvRTrees tree, int offset) {
System.out.println("!!!!! Test model with count of fires more than " + offset + "!!!!!");
//пример. номер примера, температура, влажность, сила ветра
testExample(tree, offset, 1, 28, 0.20f, 3);
testExample(tree, offset, 2, 28, 0.90f, 3);
testExample(tree, offset, 3, 35, 0.80f, 3);
testExample(tree, offset, 4, 20, 0.80f, 3);
testExample(tree, offset, 5, 25, 0.70f, 1);
testExample(tree, offset, 6, 25, 0.70f, 6);
System.out.println("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
}
private static void testExample(CvRTrees tree, int offset, int number, float temp, float humidity, float wind) {
Mat ex = new Mat(1, 3, CvType.CV_32F);
ex.put(0, 0, new float[]{temp, humidity, wind});
System.out.println("Example " + number + "(count of fires -> " + offset + "): " + ex.dump());
// предсказываем событие. 1 - событие произойдет
// в нашем случае означает, что произойдет число пожаров
System.out.println(tree.predict(ex));
// вероятность события (появления 1)
System.out.println(tree.predict_prob(ex));
}
}
Комментариев нет:
Отправить комментарий