diff --git a/Others/DataMining_BayesNetwork/BayesNetWorkTool.java b/Others/DataMining_BayesNetwork/BayesNetWorkTool.java new file mode 100644 index 0000000..cbf99ae --- /dev/null +++ b/Others/DataMining_BayesNetwork/BayesNetWorkTool.java @@ -0,0 +1,328 @@ +package DataMining_BayesNetwork; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.util.ArrayList; +import java.util.HashMap; + +/** + * ��Ҷ˹�����㷨������ + * + * @author lyq + * + */ +public class BayesNetWorkTool { + // ���ϸ��ʷֲ������ļ���ַ + private String dataFilePath; + // �¼����������ļ���ַ + private String attachFilePath; + // ���������� + private int columns; + // ���ʷֲ����� + private String[][] totalData; + // �������ݶ� + private ArrayList<String[]> attachData; + // �ڵ����б� + private ArrayList<Node> nodes; + // ������������֮��Ķ�Ӧ��ϵ + private HashMap<String, Integer> attr2Column; + + public BayesNetWorkTool(String dataFilePath, String attachFilePath) { + this.dataFilePath = dataFilePath; + this.attachFilePath = attachFilePath; + + initDatas(); + } + + /** + * ��ʼ���������ݺ��ʷֲ����� + */ + private void initDatas() { + String[] columnValues; + String[] array; + ArrayList<String> datas; + ArrayList<String> adatas; + + // ���ļ��ж�ȡ���� + datas = readDataFile(dataFilePath); + adatas = readDataFile(attachFilePath); + + columnValues = datas.get(0).split(" "); + // ���Ը����ƴ����¼�B(����)��E(����)��A(������).M(�ӵ�M�ĵ绰)��JͬM����˼, + // ����ֵ����y,n����yes������no������ + this.attr2Column = new HashMap<>(); + for (int i = 0; i < columnValues.length; i++) { + // ��������ȡ�����������У�����ֵ����ͼ�� + this.attr2Column.put(columnValues[i], i); + } + + this.columns = columnValues.length; + this.totalData = new String[datas.size()][columns]; + for (int i = 0; i < datas.size(); i++) { + this.totalData[i] = datas.get(i).split(" "); + } + + this.attachData = new ArrayList<>(); + // �����������ݶ� + for (String str : adatas) { + array = str.split(" "); + this.attachData.add(array); + } + + // ���챴Ҷ˹����ṹͼ + constructDAG(); + } + + /** + * ���ļ��ж�ȡ���� + */ + private ArrayList<String> readDataFile(String filePath) { + File file = new File(filePath); + ArrayList<String> dataArray = new ArrayList<String>(); + + try { + BufferedReader in = new BufferedReader(new FileReader(file)); + String str; + while ((str = in.readLine()) != null) { + dataArray.add(str); + } + in.close(); + } catch (IOException e) { + e.getStackTrace(); + } + + return dataArray; + } + + /** + * ���ݹ������ݹ��챴Ҷ˹����������ͼ + */ + private void constructDAG() { + // �ڵ���ڱ�ʶ + boolean srcExist; + boolean desExist; + String name1; + String name2; + Node srcNode; + Node desNode; + + this.nodes = new ArrayList<>(); + for (String[] array : this.attachData) { + srcExist = false; + desExist = false; + + name1 = array[0]; + name2 = array[1]; + + // �½��ڵ� + srcNode = new Node(name1); + desNode = new Node(name2); + + for (Node temp : this.nodes) { + // ����ҵ���ͬ�ڵ㣬��ȡ�� + if (srcNode.isEqual(temp)) { + srcExist = true; + srcNode = temp; + } else if (desNode.isEqual(temp)) { + desExist = true; + desNode = temp; + } + + // ���2���ڵ㶼���ҵ���������ѭ�� + if (srcExist && desExist) { + break; + } + } + + // ��2���ڵ�������� + srcNode.connectNode(desNode); + + // ���ݱ�ʶ�ж��Ƿ���Ҫ�����б������� + if (!srcExist) { + this.nodes.add(srcNode); + } + + if (!desExist) { + this.nodes.add(desNode); + } + } + } + + /** + * ��ѯ�������� + * + * @param attrValues + * ��������ֵ + * @return + */ + private double queryConditionPro(ArrayList<String[]> attrValues) { + // �ж��Ƿ�������������ֵ���� + boolean hasPrior; + // �ж��Ƿ������������ֵ���� + boolean hasBack; + int priorIndex; + int attrIndex; + double backPro; + double totalPro; + double pro; + double currentPro; + // �������� + String[] priorValue; + String[] tempData; + + pro = 0; + totalPro = 0; + backPro = 0; + attrValues.get(0); + priorValue = attrValues.get(0); + // �õ�������� + attrValues.remove(0); + + // ȡ���������Ե����� + priorIndex = this.attr2Column.get(priorValue[0]); + // ������һ�е����������� + for (int i = 1; i < this.totalData.length; i++) { + tempData = this.totalData[i]; + + hasPrior = false; + hasBack = true; + + // ��ǰ�еĸ��� + currentPro = Double.parseDouble(tempData[this.columns - 1]); + // �ж��Ƿ������������� + if (tempData[priorIndex].equals(priorValue[1])) { + hasPrior = true; + } + + for (String[] array : attrValues) { + attrIndex = this.attr2Column.get(array[0]); + + // �ж�ֵ�Ƿ��������� + if (!tempData[attrIndex].equals(array[1])) { + hasBack = false; + break; + } + } + + // ���м���ͳ�ƣ��ֱ��������������Ե�ֵ��ͬʱ���������ĸ��� + if (hasBack) { + backPro += currentPro; + if (hasPrior) { + totalPro += currentPro; + } + } else if (hasPrior && attrValues.size() == 0) { + // ���ֻ�����������Ϊ�����ʵļ��� + totalPro += currentPro; + backPro = 1.0; + } + } + + // �����ܵĸ���=����������/ֻ��������������ʱ����� + pro = totalPro / backPro; + + return pro; + } + + /** + * ���ݱ�Ҷ˹���������� + * + * @param queryStr + * ��ѯ������ + * @return + */ + public double calProByNetWork(String queryStr) { + double temp; + double pro; + String[] array; + // ��������ֵ + String[] preValue; + // ��������ֵ + String[] backValue; + // �������������ͺ�������ֵ������ֵ�Ļ��� + ArrayList<String[]> attrValues; + + // �ж��Ƿ���������ṹ + if (!satisfiedNewWork(queryStr)) { + return -1; + } + + pro = 1; + // ��������ѯ�����ķֽ� + array = queryStr.split(","); + + // ���ʵij�ֵ���ڵ�һ���¼�������������� + attrValues = new ArrayList<>(); + attrValues.add(array[0].split("=")); + pro = queryConditionPro(attrValues); + + for (int i = 0; i < array.length - 1; i++) { + attrValues.clear(); + + // �±�С����ǰ������ں������� + backValue = array[i].split("="); + preValue = array[i + 1].split("="); + attrValues.add(preValue); + attrValues.add(backValue); + + // �����������ĸ���ֵ + temp = queryConditionPro(attrValues); + // ���л������ + pro *= temp; + } + + return pro; + } + + /** + * ��֤�¼��IJ�ѯ�����ϵ�Ƿ����㱴Ҷ˹���� + * + * @param queryStr + * ��ѯ�ַ��� + * @return + */ + private boolean satisfiedNewWork(String queryStr) { + String attrName; + String[] array; + boolean isExist; + boolean isSatisfied; + // ��ǰ�ڵ� + Node currentNode; + // ��ѡ�ڵ��б� + ArrayList<Node> nodeList; + + isSatisfied = true; + currentNode = null; + // ����ѯ�ַ����ķֽ� + array = queryStr.split(","); + nodeList = this.nodes; + + for (String s : array) { + // ��ʼʱĬ�����Զ�Ӧ�Ľڵ㲻���� + isExist = false; + // �õ������¼��� + attrName = s.split("=")[0]; + + for (Node n : nodeList) { + if (n.name.equals(attrName)) { + isExist = true; + + currentNode = n; + // ��һ�ֵĺ�ѡ�ڵ�Ϊ��ǰ�ڵ�ĺ��ӽڵ� + nodeList = currentNode.childNodes; + + break; + } + } + + // �������δ�ҵ��Ľڵ㣬��˵�������������ṹ����ѭ�� + if (!isExist) { + isSatisfied = false; + break; + } + } + + return isSatisfied; + } +} diff --git a/Others/DataMining_BayesNetwork/Client.java b/Others/DataMining_BayesNetwork/Client.java new file mode 100644 index 0000000..98706c4 --- /dev/null +++ b/Others/DataMining_BayesNetwork/Client.java @@ -0,0 +1,32 @@ +package DataMining_BayesNetwork; + +import java.text.MessageFormat; + +/** + * ��Ҷ˹���糡�������� + * + * @author lyq + * + */ +public class Client { + public static void main(String[] args) { + String dataFilePath = "C:\\Users\\lyq\\Desktop\\icon\\input.txt"; + String attachFilePath = "C:\\Users\\lyq\\Desktop\\icon\\attach.txt"; + // ��ѯ����� + String queryStr; + // ������� + double result; + + // ��ѯ�����������¼��ǵ������ˣ������������ˣ����½ӵ�Mary�ĵ绰 + queryStr = "E=y,A=y,M=y"; + BayesNetWorkTool tool = new BayesNetWorkTool(dataFilePath, + attachFilePath); + result = tool.calProByNetWork(queryStr); + + if (result == -1) { + System.out.println("���������¼������㱴Ҷ˹����Ľṹ�����������"); + } else { + System.out.println(String.format("�¼�%s�����ĸ���Ϊ%s", queryStr, result)); + } + } +} diff --git a/Others/DataMining_BayesNetwork/Node.java b/Others/DataMining_BayesNetwork/Node.java new file mode 100644 index 0000000..bb2a07d --- /dev/null +++ b/Others/DataMining_BayesNetwork/Node.java @@ -0,0 +1,58 @@ +package DataMining_BayesNetwork; + +import java.util.ArrayList; + +/** + * ��Ҷ˹����ڵ��� + * + * @author lyq + * + */ +public class Node { + // �ڵ���������� + String name; + // �ڵ�ĸ��ڵ㣬Ҳ�������νڵ㣬���ܶ�� + ArrayList<Node> parentNodes; + // �ڵ���ӽڵ㣬Ҳ�������νڵ㣬���ܶ�� + ArrayList<Node> childNodes; + + public Node(String name) { + this.name = name; + + // ��ʼ������ + this.parentNodes = new ArrayList<>(); + this.childNodes = new ArrayList<>(); + } + + /** + * �������ڵ����ӵ�Ŀ������Ľڵ� + * + * @param node + * ���νڵ� + */ + public void connectNode(Node node) { + // �����νڵ���������ڵ�ĺ��ӽڵ��� + this.childNodes.add(node); + // �������ڵ���뵽���νڵ�ĸ��ڵ��� + node.parentNodes.add(this); + } + + /** + * �ж���Ŀ��ڵ��Ƿ���ͬ����Ҫ�Ƚ������Ƿ���ͬ���� + * + * @param node + * Ŀ���� + * @return + */ + public boolean isEqual(Node node) { + boolean isEqual; + + isEqual = false; + // �ڵ�������ͬ����Ϊ��� + if (this.name.equals(node.name)) { + isEqual = true; + } + + return isEqual; + } +} diff --git a/Others/DataMining_BayesNetwork/attach.txt b/Others/DataMining_BayesNetwork/attach.txt new file mode 100644 index 0000000..bd4bdb6 --- /dev/null +++ b/Others/DataMining_BayesNetwork/attach.txt @@ -0,0 +1,4 @@ +B A +E A +A M +A J \ No newline at end of file diff --git a/Others/DataMining_BayesNetwork/input.txt b/Others/DataMining_BayesNetwork/input.txt new file mode 100644 index 0000000..ed01889 --- /dev/null +++ b/Others/DataMining_BayesNetwork/input.txt @@ -0,0 +1,33 @@ +B E A M J P +y y y y y 0.00012 +y y y y n 0.000051 +y y y n y 0.000013 +y y y n n 0.0000057 +y y n y y 0.000000005 +y y n y n 0.00000049 +y y n n y 0.000000095 +y y n n n 0.0000094 +y n y y y 0.0058 +y n y y n 0.0025 +y n y n y 0.00065 +y n y n n 0.00028 +y n n y y 0.00000029 +y n n y n 0.000029 +y n n n y 0.0000056 +y n n n n 0.00055 +n y y y y 0.0036 +n y y y n 0.0016 +n y y n y 0.0004 +n y y n n 0.00017 +n y n y y 0.000007 +n y n y n 0.00069 +n y n n y 0.00013 +n y n n n 0.013 +n n y y y 0.00061 +n n y y n 0.00026 +n n y n y 0.000068 +n n y n n 0.000029 +n n n y y 0.00048 +n n n y n 0.048 +n n n n y 0.0092 +n n n n n 0.91 \ No newline at end of file diff --git a/Others/DataMining_TAN/AttrMutualInfo.java b/Others/DataMining_TAN/AttrMutualInfo.java new file mode 100644 index 0000000..6caf12d --- /dev/null +++ b/Others/DataMining_TAN/AttrMutualInfo.java @@ -0,0 +1,28 @@ +package DataMining_TAN; + +/** + * ����֮��Ļ���Ϣֵ����ʾ����֮��Ĺ����Դ�С + * @author lyq + * + */ +public class AttrMutualInfo implements Comparable<AttrMutualInfo>{ + //����Ϣֵ + Double value; + //��������ֵ�� + Node[] nodeArray; + + public AttrMutualInfo(double value, Node node1, Node node2){ + this.value = value; + + this.nodeArray = new Node[2]; + this.nodeArray[0] = node1; + this.nodeArray[1] = node2; + } + + @Override + public int compareTo(AttrMutualInfo o) { + // TODO Auto-generated method stub + return o.value.compareTo(this.value); + } + +} diff --git a/Others/DataMining_TAN/Client.java b/Others/DataMining_TAN/Client.java new file mode 100644 index 0000000..bd104bc --- /dev/null +++ b/Others/DataMining_TAN/Client.java @@ -0,0 +1,36 @@ +package DataMining_TAN; + +/** + * TAN�������ر�Ҷ˹�㷨 + * + * @author lyq + * + */ +public class Client { + public static void main(String[] args) { + String filePath = "C:\\Users\\lyq\\Desktop\\icon\\input.txt"; + // ������ѯ��� + String queryStr; + // ����������1 + double classResult1; + // ����������2 + double classResult2; + + TANTool tool = new TANTool(filePath); + queryStr = "OutLook=Sunny,Temperature=Hot,Humidity=High,Wind=Weak,PlayTennis=No"; + classResult1 = tool.calHappenedPro(queryStr); + + queryStr = "OutLook=Sunny,Temperature=Hot,Humidity=High,Wind=Weak,PlayTennis=Yes"; + classResult2 = tool.calHappenedPro(queryStr); + + System.out.println(String.format("���Ϊ%s����õĸ���Ϊ%s", "PlayTennis=No", + classResult1)); + System.out.println(String.format("���Ϊ%s����õĸ���Ϊ%s", "PlayTennis=Yes", + classResult2)); + if (classResult1 > classResult2) { + System.out.println("�������ΪPlayTennis=No"); + } else { + System.out.println("�������ΪPlayTennis=Yes"); + } + } +} diff --git a/Others/DataMining_TAN/Node.java b/Others/DataMining_TAN/Node.java new file mode 100644 index 0000000..f3a3b51 --- /dev/null +++ b/Others/DataMining_TAN/Node.java @@ -0,0 +1,63 @@ +package DataMining_TAN; + +import java.util.ArrayList; + +/** + * ��Ҷ˹����ڵ��� + * + * @author lyq + * + */ +public class Node { + //�ڵ�Ψһid���������ڵ����ӷ����ȷ�� + int id; + // �ڵ���������� + String name; + // �ýڵ��������Ľڵ� + ArrayList<Node> connectedNodes; + + public Node(int id, String name) { + this.id = id; + this.name = name; + + // ��ʼ������ + this.connectedNodes = new ArrayList<>(); + } + + /** + * �������ڵ����ӵ�Ŀ������Ľڵ� + * + * @param node + * ���νڵ� + */ + public void connectNode(Node node) { + //������������ + if(this.id == node.id){ + return; + } + + // ���ڵ���������ڵ�Ľڵ��б��� + this.connectedNodes.add(node); + // �������ڵ���뵽Ŀ��ڵ���б��� + node.connectedNodes.add(this); + } + + /** + * �ж���Ŀ��ڵ��Ƿ���ͬ����Ҫ�Ƚ������Ƿ���ͬ���� + * + * @param node + * Ŀ���� + * @return + */ + public boolean isEqual(Node node) { + boolean isEqual; + + isEqual = false; + // �ڵ�������ͬ����Ϊ��� + if (this.id == node.id) { + isEqual = true; + } + + return isEqual; + } +} diff --git a/Others/DataMining_TAN/TANTool.java b/Others/DataMining_TAN/TANTool.java new file mode 100644 index 0000000..56e90a6 --- /dev/null +++ b/Others/DataMining_TAN/TANTool.java @@ -0,0 +1,571 @@ +package DataMining_TAN; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.util.ArrayList; +import java.util.Collections; +import java.util.HashMap; + +/** + * TAN�������ر�Ҷ˹�㷨������ + * + * @author lyq + * + */ +public class TANTool { + // �������ݼ���ַ + private String filePath; + // ���ݼ���������,����һ������������ + private int attrNum; + // ���������� + private String classAttrName; + // ������������ + private String[] attrNames; + // ��Ҷ˹����ߵķ��������ڵ���ֵΪ�ڵ�id,��i->j + private int[][] edges; + // �����������±��ӳ�� + private HashMap<String, Integer> attr2Column; + // ���ԣ����Զ�ȡֵ����ӳ��� + private HashMap<String, ArrayList<String>> attr2Values; + // ��Ҷ˹�����ܽڵ��б� + private ArrayList<Node> totalNodes; + // �ܵIJ������� + private ArrayList<String[]> totalDatas; + + public TANTool(String filePath) { + this.filePath = filePath; + + readDataFile(); + } + + /** + * ���ļ��ж�ȡ���� + */ + private void readDataFile() { + File file = new File(filePath); + ArrayList<String[]> dataArray = new ArrayList<String[]>(); + + try { + BufferedReader in = new BufferedReader(new FileReader(file)); + String str; + String[] array; + + while ((str = in.readLine()) != null) { + array = str.split(" "); + dataArray.add(array); + } + in.close(); + } catch (IOException e) { + e.getStackTrace(); + } + + this.totalDatas = dataArray; + this.attrNames = this.totalDatas.get(0); + this.attrNum = this.attrNames.length; + this.classAttrName = this.attrNames[attrNum - 1]; + + Node node; + this.edges = new int[attrNum][attrNum]; + this.totalNodes = new ArrayList<>(); + this.attr2Column = new HashMap<>(); + this.attr2Values = new HashMap<>(); + + // �������Խڵ�id��С��Ϊ0 + node = new Node(0, attrNames[attrNum - 1]); + this.totalNodes.add(node); + for (int i = 0; i < attrNames.length; i++) { + if (i < attrNum - 1) { + // ������Ҷ˹����ڵ㣬ÿ������һ���ڵ� + node = new Node(i + 1, attrNames[i]); + this.totalNodes.add(node); + } + + // �������Ե����±��ӳ�� + this.attr2Column.put(attrNames[i], i); + } + + String[] temp; + ArrayList<String> values; + // ����������������ֵ�Ե�ӳ��ƥ�� + for (int i = 1; i < this.totalDatas.size(); i++) { + temp = this.totalDatas.get(i); + + for (int j = 0; j < temp.length; j++) { + // �ж�map���Ƿ������������ + if (this.attr2Values.containsKey(attrNames[j])) { + values = this.attr2Values.get(attrNames[j]); + } else { + values = new ArrayList<>(); + } + + if (!values.contains(temp[j])) { + // �����µ�����ֵ + values.add(temp[j]); + } + + this.attr2Values.put(attrNames[j], values); + } + } + } + + /** + * ������������Ϣ�ȶԹ������Ȩ�ؿ����,���ص�һ���ڵ�Ϊ���ڵ� + * + * @param iArray + */ + private Node constructWeightTree(ArrayList<Node[]> iArray) { + Node node1; + Node node2; + Node root; + ArrayList<Node> existNodes; + + existNodes = new ArrayList<>(); + + for (Node[] i : iArray) { + node1 = i[0]; + node2 = i[1]; + + // ��2���ڵ�������� + node1.connectNode(node2); + // ������ֻ�·���� + addIfNotExist(node1, existNodes); + addIfNotExist(node2, existNodes); + + if (existNodes.size() == attrNum - 1) { + break; + } + } + + // ���ص�һ����Ϊ���ڵ� + root = existNodes.get(0); + return root; + } + + /** + * Ϊ���ͽṹȷ���ߵķ�����Ϊ���Ը��ڵ㷽��ָ���������Խڵ㷽�� + * + * @param root + * ��ǰ�������Ľڵ� + */ + private void confirmGraphDirection(Node currentNode) { + int i; + int j; + ArrayList<Node> connectedNodes; + + connectedNodes = currentNode.connectedNodes; + + i = currentNode.id; + for (Node n : connectedNodes) { + j = n.id; + + // �ж����Ӵ�2�ڵ�ķ����Ƿ�ȷ�� + if (edges[i][j] == 0 && edges[j][i] == 0) { + // ���û��ȷ�������ƶ�����Ϊi->j + edges[i][j] = 1; + + // �ݹ�������� + confirmGraphDirection(n); + } + } + } + + /** + * Ϊ���Խڵ����ӷ������Խڵ�Ϊ���ڵ� + * + * @param parentNode + * ���ڵ� + * @param nodeList + * �ӽڵ��б� + */ + private void addParentNode() { + // �������Խڵ� + Node parentNode; + + parentNode = null; + for (Node n : this.totalNodes) { + if (n.id == 0) { + parentNode = n; + break; + } + } + + for (Node child : this.totalNodes) { + parentNode.connectNode(child); + + if (child.id != 0) { + // ȷ�����ӷ��� + this.edges[0][child.id] = 1; + } + } + } + + /** + * �ڽڵ㼯�������ӽڵ� + * + * @param node + * �����ӽڵ� + * @param existNodes + * �Ѵ��ڵĽڵ��б� + * @return + */ + public boolean addIfNotExist(Node node, ArrayList<Node> existNodes) { + boolean canAdd; + + canAdd = true; + for (Node n : existNodes) { + // ����ڵ��б����Ѿ����нڵ㣬��������ʧ�� + if (n.isEqual(node)) { + canAdd = false; + break; + } + } + + if (canAdd) { + existNodes.add(node); + } + + return canAdd; + } + + /** + * ����ڵ��������� + * + * @param node + * ����node�ĺ������ + * @param queryParam + * ��ѯ�����Բ��� + * @return + */ + private double calConditionPro(Node node, HashMap<String, String> queryParam) { + int id; + double pro; + String value; + String[] attrValue; + + ArrayList<String[]> priorAttrInfos; + ArrayList<String[]> backAttrInfos; + ArrayList<Node> parentNodes; + + pro = 1; + id = node.id; + parentNodes = new ArrayList<>(); + priorAttrInfos = new ArrayList<>(); + backAttrInfos = new ArrayList<>(); + + for (int i = 0; i < this.edges.length; i++) { + // Ѱ�Ҹ��ڵ�id + if (this.edges[i][id] == 1) { + for (Node temp : this.totalNodes) { + // Ѱ��Ŀ��ڵ�id + if (temp.id == i) { + parentNodes.add(temp); + break; + } + } + } + } + + // ��ȡ�������Ե�����ֵ,���������������� + value = queryParam.get(node.name); + attrValue = new String[2]; + attrValue[0] = node.name; + attrValue[1] = value; + priorAttrInfos.add(attrValue); + + // ��һ���Ӻ������� + for (Node p : parentNodes) { + value = queryParam.get(p.name); + attrValue = new String[2]; + attrValue[0] = p.name; + attrValue[1] = value; + + backAttrInfos.add(attrValue); + } + + pro = queryConditionPro(priorAttrInfos, backAttrInfos); + + return pro; + } + + /** + * ��ѯ�������� + * + * @param attrValues + * ��������ֵ + * @return + */ + private double queryConditionPro(ArrayList<String[]> priorValues, + ArrayList<String[]> backValues) { + // �ж��Ƿ�������������ֵ���� + boolean hasPrior; + // �ж��Ƿ������������ֵ���� + boolean hasBack; + int attrIndex; + double backPro; + double totalPro; + double pro; + String[] tempData; + + pro = 0; + totalPro = 0; + backPro = 0; + + // ������һ�е����������� + for (int i = 1; i < this.totalDatas.size(); i++) { + tempData = this.totalDatas.get(i); + + hasPrior = true; + hasBack = true; + + // �ж��Ƿ������������� + for (String[] array : priorValues) { + attrIndex = this.attr2Column.get(array[0]); + + // �ж�ֵ�Ƿ��������� + if (!tempData[attrIndex].equals(array[1])) { + hasPrior = false; + break; + } + } + + // �ж��Ƿ������������ + for (String[] array : backValues) { + attrIndex = this.attr2Column.get(array[0]); + + // �ж�ֵ�Ƿ��������� + if (!tempData[attrIndex].equals(array[1])) { + hasBack = false; + break; + } + } + + // ���м���ͳ�ƣ��ֱ��������������Ե�ֵ��ͬʱ���������ĸ��� + if (hasBack) { + backPro++; + if (hasPrior) { + totalPro++; + } + } else if (hasPrior && backValues.size() == 0) { + // ���ֻ�����������Ϊ�����ʵļ��� + totalPro++; + backPro = 1.0; + } + } + + if (backPro == 0) { + pro = 0; + } else { + // �����ܵĸ���=����������/ֻ��������������ʱ����� + pro = totalPro / backPro; + } + + return pro; + } + + /** + * �����ѯ�������������㷢������ + * + * @param queryParam + * �������� + * @return + */ + public double calHappenedPro(String queryParam) { + double result; + double temp; + // ��������ֵ + String classAttrValue; + String[] array; + String[] array2; + HashMap<String, String> params; + + result = 1; + params = new HashMap<>(); + + // ���в�ѯ�ַ��IJ����ֽ� + array = queryParam.split(","); + for (String s : array) { + array2 = s.split("="); + params.put(array2[0], array2[1]); + } + + classAttrValue = params.get(classAttrName); + // ������Ҷ˹����ṹ + constructBayesNetWork(classAttrValue); + + for (Node n : this.totalNodes) { + temp = calConditionPro(n, params); + + // Ϊ�˱��������������Ϊ0�������������� + if (temp == 0) { + temp = 0.001; + } + + // �������ϸ��ʹ�ʽ�����г˻����� + result *= temp; + } + + return result; + } + + /** + * �������ͱ�Ҷ˹����ṹ + * + * @param value + * �����ֵ + */ + private void constructBayesNetWork(String value) { + Node rootNode; + ArrayList<AttrMutualInfo> mInfoArray; + // ����Ϣ�ȶ� + ArrayList<Node[]> iArray; + + iArray = null; + rootNode = null; + + // ��ÿ�����¹�����Ҷ˹����ṹ��ʱ�����ԭ�е����ӽṹ + for (Node n : this.totalNodes) { + n.connectedNodes.clear(); + } + this.edges = new int[attrNum][attrNum]; + + // �ӻ���Ϣ������ȡ������ֵ�� + iArray = new ArrayList<>(); + mInfoArray = calAttrMutualInfoArray(value); + for (AttrMutualInfo v : mInfoArray) { + iArray.add(v.nodeArray); + } + + // �������Ȩ�ؿ���� + rootNode = constructWeightTree(iArray); + // Ϊ����ͼȷ���ߵķ��� + confirmGraphDirection(rootNode); + // Ϊÿ�����Խڵ����ӷ������Ը��ڵ� + addParentNode(); + } + + /** + * �����������ֵ����������֮��Ļ���Ϣֵ + * + * @param value + * �������ֵ + * @return + */ + private ArrayList<AttrMutualInfo> calAttrMutualInfoArray(String value) { + double iValue; + Node node1; + Node node2; + AttrMutualInfo mInfo; + ArrayList<AttrMutualInfo> mInfoArray; + + mInfoArray = new ArrayList<>(); + + for (int i = 0; i < this.totalNodes.size() - 1; i++) { + node1 = this.totalNodes.get(i); + // �����������Խڵ� + if (node1.id == 0) { + continue; + } + + for (int j = i + 1; j < this.totalNodes.size(); j++) { + node2 = this.totalNodes.get(j); + // �����������Խڵ� + if (node2.id == 0) { + continue; + } + + // ����2�����Խڵ�֮��Ļ���Ϣֵ + iValue = calMutualInfoValue(node1, node2, value); + mInfo = new AttrMutualInfo(iValue, node1, node2); + mInfoArray.add(mInfo); + } + } + + // ��������н������У��û���Ϣֵ�ߵ��������ڹ����� + Collections.sort(mInfoArray); + + return mInfoArray; + } + + /** + * ����2�����Խڵ�Ļ���Ϣֵ + * + * @param node1 + * �ڵ�1 + * @param node2 + * �ڵ�2 + * @param vlaue + * �������ֵ + */ + private double calMutualInfoValue(Node node1, Node node2, String value) { + double iValue; + double temp; + // ���ֲ�ͬ�����ĺ������ + double pXiXj; + double pXi; + double pXj; + String[] array1; + String[] array2; + ArrayList<String> attrValues1; + ArrayList<String> attrValues2; + ArrayList<String[]> priorValues; + // ������ʣ���������������ֵ + ArrayList<String[]> backValues; + + array1 = new String[2]; + array2 = new String[2]; + priorValues = new ArrayList<>(); + backValues = new ArrayList<>(); + + iValue = 0; + array1[0] = classAttrName; + array1[1] = value; + // �������Զ��������� + backValues.add(array1); + + // ��ȡ�ڵ����Ե�����ֵ���� + attrValues1 = this.attr2Values.get(node1.name); + attrValues2 = this.attr2Values.get(node2.name); + + for (String v1 : attrValues1) { + for (String v2 : attrValues2) { + priorValues.clear(); + + array1 = new String[2]; + array1[0] = node1.name; + array1[1] = v1; + priorValues.add(array1); + + array2 = new String[2]; + array2[0] = node2.name; + array2[1] = v2; + priorValues.add(array2); + + // ����3�������µĸ��� + pXiXj = queryConditionPro(priorValues, backValues); + + priorValues.clear(); + priorValues.add(array1); + pXi = queryConditionPro(priorValues, backValues); + + priorValues.clear(); + priorValues.add(array2); + pXj = queryConditionPro(priorValues, backValues); + + // �����������һ����������Ϊ0����ֱ�Ӹ�ֵΪ0���� + if (pXiXj == 0 || pXi == 0 || pXj == 0) { + temp = 0; + } else { + // ���ù�ʽ������Դ�����ֵ����ϵĸ��� + temp = pXiXj * Math.log(pXiXj / (pXi * pXj)) / Math.log(2); + } + + // ���к�����ֵ����ϵ��ۼӼ�Ϊ�������ԵĻ���Ϣֵ + iValue += temp; + } + } + + return iValue; + } +} diff --git a/Others/DataMining_TAN/input.txt b/Others/DataMining_TAN/input.txt new file mode 100644 index 0000000..aea7074 --- /dev/null +++ b/Others/DataMining_TAN/input.txt @@ -0,0 +1,15 @@ +OutLook Temperature Humidity Wind PlayTennis +Sunny Hot High Weak No +Sunny Hot High Strong No +Overcast Hot High Weak Yes +Rainy Mild High Weak Yes +Rainy Cool Normal Weak Yes +Rainy Cool Normal Strong No +Overcast Cool Normal Strong Yes +Sunny Mild High Weak No +Sunny Cool Normal Weak Yes +Rainy Mild Normal Weak Yes +Sunny Mild Normal Strong Yes +Overcast Mild High Strong Yes +Overcast Hot Normal Weak Yes +Rainy Mild High Strong No \ No newline at end of file diff --git a/Others/DataMining_Viterbi/BaseNames.java b/Others/DataMining_Viterbi/BaseNames.java new file mode 100644 index 0000000..cca0aaa --- /dev/null +++ b/Others/DataMining_Viterbi/BaseNames.java @@ -0,0 +1,24 @@ +package DataMining_Viterbi; + +/** + * �������������� + * @author lyq + * + */ +public class BaseNames { + //���������±� + public static final int DAY1 = 0; + public static final int DAY2 = 1; + public static final int DAY3 = 2; + + //����������� + public static final int WEATHER_SUNNY = 0; + public static final int WEATHER_CLOUDY = 1; + public static final int WEATHER_RAINY = 2; + + //ʪ��������� + public static final int HUMIDITY_DRY = 0; + public static final int HUMIDITY_DRYISH = 1; + public static final int HUMIDITY_DAMP = 1; + public static final int HUMIDITY_SOGGY = 1; +} diff --git a/Others/DataMining_Viterbi/Client.java b/Others/DataMining_Viterbi/Client.java new file mode 100644 index 0000000..577eabd --- /dev/null +++ b/Others/DataMining_Viterbi/Client.java @@ -0,0 +1,31 @@ +package DataMining_Viterbi; + +/** + * ά�ر��㷨 + * + * @author lyq + * + */ +public class Client { + public static void main(String[] args) { + // ״̬ת�Ƹ��ʾ���·�� + String stmFilePath; + // ��������·�� + String cfFilePath; + // �۲쵽��״̬ + String[] observeStates; + // ��ʼ״̬ + double[] initStatePro; + ViterbiTool tool; + + stmFilePath = "C:\\Users\\lyq\\Desktop\\icon\\stmatrix.txt"; + cfFilePath = "C:\\Users\\lyq\\Desktop\\icon\\humidity-matrix.txt"; + + initStatePro = new double[] { 0.63, 0.17, 0.20 }; + observeStates = new String[] { "Dry", "Damp", "Soggy" }; + + tool = new ViterbiTool(stmFilePath, cfFilePath, initStatePro, + observeStates); + tool.calHMMObserve(); + } +} diff --git a/Others/DataMining_Viterbi/ViterbiTool.java b/Others/DataMining_Viterbi/ViterbiTool.java new file mode 100644 index 0000000..6f1ade6 --- /dev/null +++ b/Others/DataMining_Viterbi/ViterbiTool.java @@ -0,0 +1,240 @@ +package DataMining_Viterbi; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.Map; + +/** + * ά�ر��㷨������ + * + * @author lyq + * + */ +public class ViterbiTool { + // ״̬ת�Ƹ��ʾ����ļ���ַ + private String stmFilePath; + // ���������ļ���ַ + private String confusionFilePath; + // ��ʼ״̬���� + private double[] initStatePro; + // �۲쵽��״̬���� + public String[] observeStates; + // ״̬ת�ƾ���ֵ + private double[][] stMatrix; + // ��������ֵ + private double[][] confusionMatrix; + // ���������µ�DZ����������ֵ + private double[][] potentialValues; + // DZ������ + private ArrayList<String> potentialAttrs; + // ����ֵ������ӳ��ͼ + private HashMap<String, Integer> name2Index; + // ����������ֵӳ��ͼ + private HashMap<Integer, String> index2name; + + public ViterbiTool(String stmFilePath, String confusionFilePath, + double[] initStatePro, String[] observeStates) { + this.stmFilePath = stmFilePath; + this.confusionFilePath = confusionFilePath; + this.initStatePro = initStatePro; + this.observeStates = observeStates; + + initOperation(); + } + + /** + * ��ʼ�����ݲ��� + */ + private void initOperation() { + double[] temp; + int index; + ArrayList<String[]> smtDatas; + ArrayList<String[]> cfDatas; + + smtDatas = readDataFile(stmFilePath); + cfDatas = readDataFile(confusionFilePath); + + index = 0; + this.stMatrix = new double[smtDatas.size()][]; + for (String[] array : smtDatas) { + temp = new double[array.length]; + for (int i = 0; i < array.length; i++) { + try { + temp[i] = Double.parseDouble(array[i]); + } catch (NumberFormatException e) { + temp[i] = -1; + } + } + + // ��ת�����ֵ���������� + this.stMatrix[index] = temp; + index++; + } + + index = 0; + this.confusionMatrix = new double[cfDatas.size()][]; + for (String[] array : cfDatas) { + temp = new double[array.length]; + for (int i = 0; i < array.length; i++) { + try { + temp[i] = Double.parseDouble(array[i]); + } catch (NumberFormatException e) { + temp[i] = -1; + } + } + + // ��ת�����ֵ���������� + this.confusionMatrix[index] = temp; + index++; + } + + this.potentialAttrs = new ArrayList<>(); + // ����DZ���������� + for (String s : smtDatas.get(0)) { + this.potentialAttrs.add(s); + } + // ȥ��������Ч�� + potentialAttrs.remove(0); + + this.name2Index = new HashMap<>(); + this.index2name = new HashMap<>(); + + // ���������±�ӳ���ϵ + for (int i = 1; i < smtDatas.get(0).length; i++) { + this.name2Index.put(smtDatas.get(0)[i], i); + // �����±굽���Ƶ�ӳ�� + this.index2name.put(i, smtDatas.get(0)[i]); + } + + for (int i = 1; i < cfDatas.get(0).length; i++) { + this.name2Index.put(cfDatas.get(0)[i], i); + } + } + + /** + * ���ļ��ж�ȡ���� + */ + private ArrayList<String[]> readDataFile(String filePath) { + File file = new File(filePath); + ArrayList<String[]> dataArray = new ArrayList<String[]>(); + + try { + BufferedReader in = new BufferedReader(new FileReader(file)); + String str; + String[] tempArray; + while ((str = in.readLine()) != null) { + tempArray = str.split(" "); + dataArray.add(tempArray); + } + in.close(); + } catch (IOException e) { + e.getStackTrace(); + } + + return dataArray; + } + + /** + * ���ݹ۲������������ص��������ʾ��� + */ + private void calPotencialProMatrix() { + String curObserveState; + // �۲�������DZ���������±� + int osIndex; + int psIndex; + double temp; + double maxPro; + // �����������ֵ���������Ӱ������ظ��� + double confusionPro; + + this.potentialValues = new double[observeStates.length][potentialAttrs + .size() + 1]; + for (int i = 0; i < this.observeStates.length; i++) { + curObserveState = this.observeStates[i]; + osIndex = this.name2Index.get(curObserveState); + maxPro = -1; + + // ��Ϊ�ǵ�һ���۲�������û��ǰ���Ӱ�죬���ݳ�ʼ״̬���� + if (i == 0) { + for (String attr : this.potentialAttrs) { + psIndex = this.name2Index.get(attr); + confusionPro = this.confusionMatrix[psIndex][osIndex]; + + temp = this.initStatePro[psIndex - 1] * confusionPro; + this.potentialValues[BaseNames.DAY1][psIndex] = temp; + } + } else { + // �����DZ��������ǰһ��������Ӱ�죬�Լ���ǰ�Ļ�������Ӱ�� + for (String toDayAttr : this.potentialAttrs) { + psIndex = this.name2Index.get(toDayAttr); + confusionPro = this.confusionMatrix[psIndex][osIndex]; + + int index; + maxPro = -1; + // ͨ������ĸ��ʼ������������������� + for (String yAttr : this.potentialAttrs) { + index = this.name2Index.get(yAttr); + temp = this.potentialValues[i - 1][index] + * this.stMatrix[index][psIndex]; + + // ����õ������DZ�������������� + if (temp > maxPro) { + maxPro = temp; + } + } + + this.potentialValues[i][psIndex] = maxPro * confusionPro; + } + } + } + } + + /** + * ����ͬʱ��������ֵ���DZ������ֵ + */ + private void outputResultAttr() { + double maxPro; + int maxIndex; + ArrayList<String> psValues; + + psValues = new ArrayList<>(); + for (int i = 0; i < this.potentialValues.length; i++) { + maxPro = -1; + maxIndex = 0; + + for (int j = 0; j < potentialValues[i].length; j++) { + if (this.potentialValues[i][j] > maxPro) { + maxPro = potentialValues[i][j]; + maxIndex = j; + } + } + + // ȡ���������±��Ӧ��DZ������ + psValues.add(this.index2name.get(maxIndex)); + } + + System.out.println("�۲�����Ϊ��"); + for (String s : this.observeStates) { + System.out.print(s + ", "); + } + System.out.println(); + + System.out.println("DZ������Ϊ��"); + for (String s : psValues) { + System.out.print(s + ", "); + } + System.out.println(); + } + + /** + * ���ݹ۲����ԣ��õ�DZ��������Ϣ + */ + public void calHMMObserve() { + calPotencialProMatrix(); + outputResultAttr(); + } +} diff --git a/Others/DataMining_Viterbi/humidity-matrix.txt b/Others/DataMining_Viterbi/humidity-matrix.txt new file mode 100644 index 0000000..ff41df6 --- /dev/null +++ b/Others/DataMining_Viterbi/humidity-matrix.txt @@ -0,0 +1,4 @@ +# Dry Dryish Damp Soggy +Sunny 0.6 0.2 0.15 0.05 +Cloudy 0.25 0.25 0.25 0.25 +Rainy 0.05 0.10 0.35 0.50 \ No newline at end of file diff --git a/Others/DataMining_Viterbi/stmatrix.txt b/Others/DataMining_Viterbi/stmatrix.txt new file mode 100644 index 0000000..af66956 --- /dev/null +++ b/Others/DataMining_Viterbi/stmatrix.txt @@ -0,0 +1,4 @@ +# Sunny Cloudy Rainy +Sunny 0.5 0.375 0.125 +Cloudy 0.25 0.125 0.625 +Rainy 0.25 0.375 0.375 \ No newline at end of file diff --git a/README.md b/README.md index 02100cd..7dd82f0 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,45 @@ # 数据挖掘算法 -##18大经典DM算法 +## 算法目录 +#### 18大DM算法 +包名 | 目录名 | 算法名 | +-----| ------ |--------| +AssociationAnalysis | DataMining_Apriori | Apriori-关联规则挖掘算法 +AssociationAnalysis | DataMining_FPTree | FPTree-频繁模式树算法 +BaggingAndBoosting | DataMining_AdaBoost | AdaBoost-装袋提升算法 +Classification | DataMining_CART | CART-分类回归树算法 +Classification | DataMining_ID3 | ID3-决策树分类算法 +Classification | DataMining_KNN | KNN-k最近邻算法工具类 +Classification | DataMining_NaiveBayes | NaiveBayes-朴素贝叶斯算法 +Clustering | DataMining_BIRCH | BIRCH-层次聚类算法 +Clustering | DataMining_KMeans | KMeans-K均值算法 +GraphMining | DataMining_GSpan | GSpan-频繁子图挖掘算法 +IntegratedMining | DataMining_CBA | CBA-基于关联规则的分类算法 +LinkMining | DataMining_HITS | HITS-链接分析算法 +LinkMining | DataMining_PageRank | PageRank-网页重要性/排名算法 +RoughSets | DataMining_RoughSets | RoughSets-粗糙集属性约简算法 +SequentialPatterns | DataMining_GSP | GSP-序列模式分析算法 +SequentialPatterns | DataMining_PrefixSpan | PrefixSpan-序列模式分析算法 +StatisticalLearning | DataMining_EM | EM-期望最大化算法 +StatisticalLearning | DataMining_SVM | SVM-支持向量机算法 + +#### 其他经典DM算法 +包名 | 目录名 | 算法名 | +-----| ------ |--------| +Others | DataMining_ACO | ACO-蚁群算法 +Others | DataMining_BayesNetwork | BayesNetwork-贝叶斯网络算法 +Others | DataMining_CABDDCC | CABDDCC-基于连通图的分裂聚类算法 +Others | DataMining_Chameleon | Chameleon-两阶段合并聚类算法 +Others | DataMining_DBSCAN | DBSCAN-基于密度的聚类算法 +Others | DataMining_GA | GA-遗传算法 +Others | DataMining_GA_Maze | GA_Maze-遗传算法在走迷宫游戏中的应用算法 +Others | DataMining_KDTree | KDTree-k维空间关键数据检索算法工具类 +Others | DataMining_MSApriori | MSApriori-基于多支持度的Apriori算法 +Others | DataMining_RandomForest | RandomForest-随机森林算法 +Others | DataMining_TAN | TAN-树型朴素贝叶斯算法 +Others | DataMining_Viterbi | Viterbi-维特比算法 + +## 18大经典DM算法 18大数据挖掘的经典算法以及代码实现,涉及到了决策分类,聚类,链接挖掘,关联挖掘,模式挖掘等等方面,后面都是相应算法的博文链接,希望能够帮助大家学。 目前追加了其他的一些经典的DM算法,在others的包中涉及聚类,分类,图算法,搜索算等等,没有具体分类。 @@ -86,3 +125,18 @@ K-Dimension Tree。多维空间划分树,数据在多维空间进行划分与 * ### ACO 蚁群算法。蚁群算法又称为蚂蚁算法。同GA遗传算法类似,也是运用了大自然规律的算法,用于在图中寻找最优路径的概率型算法。灵感来源于蚂蚁在寻找食物时会散播信息素的发现路径行为。[详细介绍链接](http://blog.csdn.net/androidlushangderen/article/details/45395491) + +* ### BayesNetwork +贝叶斯网络算法。弥补了朴素贝叶斯算法中必须要事件独立性的缺点,利用了贝叶斯网络的DAG有向无环图,允许各个事件保留一定的依赖关系,网络结构中的每个节点代表一种属性,边代表相应的条件概率值,通过计算从而能得到精准的分类效果。[详细介绍链接](http://blog.csdn.net/androidlushangderen/article/details/46683729) + +* ### TAN +树型朴素贝叶斯算法。此算法又被称为加强版朴素贝叶斯算法。在满足原有朴素贝叶斯条件的基础上,他允许部条件属性直接的关联性。形成树型的结构。[详细介绍链接](http://blog.csdn.net/androidlushangderen/article/details/46763427) + +* ### Viterbi +维特比算法。给定一个隐马尔科夫模型以及一个观察序列,求出潜在的状态序列信息,每个潜在状态信息又会受到前一个状态信息的影响。 + +## 算法使用方法 +在每个算法中给出了3大类型,主算法程序,调用程序,输入数据,调用方法如下: +* 将需要数据的测试数据转化成与给定的输入格式相同 +* 然后以Client类的测试程序调用方式进行使用。 +* 也可以自行修改算法程序,来适用于自己的使用场景