【发布时间】:2020-01-04 10:28:56
【问题描述】:
我一直在寻找使用 weka 实现 KNN 的实际示例,但我发现的所有内容都太笼统了,无法理解它需要能够工作的数据(或者可能如何制作它需要的对象)工作)以及它显示的结果,也许以前使用过它的人有一个更好的例子,比如现实的事物(产品、电影、书籍等),而不是你在代数上看到的典型字母。
所以我可以弄清楚如何在我的案例中实施它(这是向使用 KNN 的活跃用户推荐菜肴),将不胜感激,谢谢。
我试图通过这个链接来理解https://www.ibm.com/developerworks/library/os-weka3/index.html,但我什至不明白他们是如何得到这个结果的,他们是如何得到公式的
第 1 步:确定距离公式
Distance = SQRT( ((58 - Age)/(69-35))^2) + ((51000 - Income)/(150000-38000))^2 )
为什么总是 /(69-35) 和 /(150000-38000) ?
编辑:
这是我尝试过但没有成功的代码,如果有人可以为我清除它,我很感激,我也通过结合这 2 个答案来完成此代码:
这个答案显示了如何获得 knn:
How to get the nearest neighbor in weka using java
这个告诉我如何创建实例(我真的不知道它们对 weka 是什么)Adding a new Instance in weka
所以我想出了这个:
public class Wekatest {
public static void main(String[] args) {
ArrayList<Attribute> atts = new ArrayList<>();
ArrayList<String> classVal = new ArrayList<>();
// I don't really understand whats happening here
classVal.add("A");
classVal.add("B");
classVal.add("C");
classVal.add("D");
classVal.add("E");
classVal.add("F");
atts.add(new Attribute("content", (ArrayList<String>) null));
atts.add(new Attribute("@@class@@", classVal));
// Here in my case the data to evaluate are dishes (plato mean dish in spanish)
Instances dataRaw = new Instances("TestInstancesPlatos", atts, 0);
// I imagine that every instance is like an Object that will be compared with the other instances, to get its neaerest neightbours (so an instance is like a dish for me)..
double[] instanceValue1 = new double[dataRaw.numAttributes()];
instanceValue1[0] = dataRaw.attribute(0).addStringValue("Pizzas");
instanceValue1[1] = 0;
dataRaw.add(new DenseInstance(1.0, instanceValue1));
double[] instanceValue2 = new double[dataRaw.numAttributes()];
instanceValue2[0] = dataRaw.attribute(0).addStringValue("Tunas");
instanceValue2[1] = 1;
dataRaw.add(new DenseInstance(1.0, instanceValue2));
double[] instanceValue3 = new double[dataRaw.numAttributes()];
instanceValue3[0] = dataRaw.attribute(0).addStringValue("Pizzas");
instanceValue3[1] = 2;
dataRaw.add(new DenseInstance(1.0, instanceValue3));
double[] instanceValue4 = new double[dataRaw.numAttributes()];
instanceValue4[0] = dataRaw.attribute(0).addStringValue("Hamburguers");
instanceValue4[1] = 3;
dataRaw.add(new DenseInstance(1.0, instanceValue4));
double[] instanceValue5 = new double[dataRaw.numAttributes()];
instanceValue5[0] = dataRaw.attribute(0).addStringValue("Pizzas");
instanceValue5[1] = 4;
dataRaw.add(new DenseInstance(1.0, instanceValue5));
System.out.println("---------------------");
weka.core.neighboursearch.LinearNNSearch knn = new LinearNNSearch(dataRaw);
try {
// This method receives the goal instance which you wanna know its neighbours and N (I don't really know what N is but I imagine it is the number of neighbours I want)
Instances nearestInstances = knn.kNearestNeighbours(dataRaw.get(0), 1);
// I expected the output to be the closes neighbour to dataRaw.get(0) which would be Pizzas, but instead I got some data that I don't really understand.
System.out.println(nearestInstances);
} catch (Exception e) {
e.printStackTrace();
}
}
}
OUTPUT:
---------------------
@relation TestInstancesPlatos
@attribute content string
@attribute @@class@@ {A,B,C,D,E,F}
@data
Pizzas,A
Tunas,B
Pizzas,C
Hamburguers,D
使用了weka依赖:
<dependency>
<groupId>nz.ac.waikato.cms.weka</groupId>
<artifactId>weka-stable</artifactId>
<version>3.8.0</version>
</dependency>
【问题讨论】:
-
69 是最高年龄,35 是最小年龄,减法得到你的范围,这将 58(我们想要找到距离的观察)与其他观察的差异标准化,但缩放到下降在 0(相等)和 1(最大可能差异)之间。这是根据收入和年龄来完成的,收入的规模大不相同。
-
@RobinGertenbach 谢谢你的称赞!