diff options
| author | ziejd2 | 2017-09-14 16:17:47 -0500 |
|---|---|---|
| committer | GitHub | 2017-09-14 16:17:47 -0500 |
| commit | 7cc31810d53176e805532b2789955f4eedbce6bb (patch) | |
| tree | 82924642070d871f753ee41c0f3e363ff8f380da | |
| parent | 6882395afdadf4e982b25b5215071a0932730950 (diff) | |
| download | BNW-7cc31810d53176e805532b2789955f4eedbce6bb.tar.gz | |
Add files via upload
Adding the *.m files used in parameter learning.
| -rw-r--r-- | BNW_parameter_learning/Predictmultiple.m | 57 | ||||
| -rw-r--r-- | BNW_parameter_learning/Predictmultipleintrvention.m | 73 | ||||
| -rw-r--r-- | BNW_parameter_learning/checkDiscreteNodes.m | 37 | ||||
| -rw-r--r-- | BNW_parameter_learning/checkStructure.m | 78 | ||||
| -rw-r--r-- | BNW_parameter_learning/drawFigure.m | 383 | ||||
| -rw-r--r-- | BNW_parameter_learning/drawFigureM.m | 258 | ||||
| -rw-r--r-- | BNW_parameter_learning/getParams.m | 22 | ||||
| -rw-r--r-- | BNW_parameter_learning/parameterLearning.m | 17 | ||||
| -rw-r--r-- | BNW_parameter_learning/readInput.m | 70 | ||||
| -rw-r--r-- | BNW_parameter_learning/readInputData.m | 75 | ||||
| -rw-r--r-- | BNW_parameter_learning/readInputStructure.m | 72 | ||||
| -rw-r--r-- | BNW_parameter_learning/runBN_initial.m | 98 | ||||
| -rw-r--r-- | BNW_parameter_learning/standardizeData.m | 25 |
13 files changed, 1265 insertions, 0 deletions
diff --git a/BNW_parameter_learning/Predictmultiple.m b/BNW_parameter_learning/Predictmultiple.m new file mode 100644 index 00000000..c14b516c --- /dev/null +++ b/BNW_parameter_learning/Predictmultiple.m @@ -0,0 +1,57 @@ +function Predictmultiple(pre) + +dfile=strcat(pre,'structure_input.txt'); +sfile=dfile; +dfile=strcat(pre,'continuous_input.txt'); +nnodefile=strcat(pre,'nnode.txt'); +fnnode = fopen(nnodefile,'r'); +nnodes = fscanf(fnnode,'%d'); + + + +%nnodes=5; +Std_flag=true; +[labels,cases,bnet]=readInput(dfile,sfile,nnodes,Std_flag); + + +%name +%labels +%map + +[bnet]=parameterLearning(bnet,cases); +%[predict_mean,predict_sd,q_sq]=looCrossValid(bnet,cases); +fvarfile=strcat(pre,'var.txt'); + +fvar = fopen(fvarfile,'r'); + +select_var_new = fscanf(fvar,'%d'); + +fvardfile=strcat(pre,'vardata.txt'); + +fvard = fopen(fvardfile,'r'); + +select_var_data_new = fscanf(fvard,'%f'); + +filename=strcat(pre,'net_figure_new.txt'); + +drawFigureM(nnodes,bnet,labels,filename,cases,select_var_new,select_var_data_new); + +%quit force; +%marginal_nodes(engine,2) +%marginal_nodes(engine,3) +%marginal_nodes(engine,4) +%marginal_nodes(engine,5) +%evidence{1}=2; +%[engine,loglik]=enter_evidence(engine,evidence) +%marginal_nodes(engine,1) +%marginal_nodes(engine,2) +%marginal_nodes(engine,3) +%marginal_nodes(engine,4) +%marginal_nodes(engine,5) +%evidence{2}=0.6; +%evidence{1}=[]; +%[engine,loglik]=enter_evidence(engine,evidence); +%marginal_nodes(engine,3); +%marginal_nodes(engine,4); +%marginal_nodes(engine,5); +end \ No newline at end of file diff --git a/BNW_parameter_learning/Predictmultipleintrvention.m b/BNW_parameter_learning/Predictmultipleintrvention.m new file mode 100644 index 00000000..4675b846 --- /dev/null +++ b/BNW_parameter_learning/Predictmultipleintrvention.m @@ -0,0 +1,73 @@ +function Predictmultipleintrvention(pre) +dfile=strcat(pre,'structure_input.txt'); +sfile=dfile; +dfile=strcat(pre,'continuous_input.txt'); +nnodefile=strcat(pre,'nnode.txt'); + +fnnode = fopen(nnodefile,'r'); +nnodes = fscanf(fnnode,'%d'); + +fvarnamefile=strcat(pre,'varname.txt'); + +varfile = fopen(fvarnamefile,'r'); + +%nnodes=5; +Std_flag=true; +[labels,cases,bnet]=readInput(dfile,sfile,nnodes,Std_flag); +[bnet]=parameterLearning(bnet,cases); + +%[predict_mean,predict_sd,q_sq]=looCrossValid(bnet,cases); + + +fvarfile=strcat(pre,'var.txt'); +fvar = fopen(fvarfile,'r'); + +select_var_new = fscanf(fvar,'%d'); + +nm = numel(select_var_new); + +varlabels = cell(1,nm); +varbuffer = fgetl(varfile); %get header line as a string +for j=1:nm + [varnext,varbuffer] = strtok(varbuffer); + varlabels{j} = varnext; + for i=1:nnodes + if strcmp(varlabels{j},labels{i}) + select_var_new(j)=i; + end + end + +end + + + + +fvardfile=strcat(pre,'vardata.txt'); + +fvard = fopen(fvardfile,'r'); + +select_var_data_new = fscanf(fvard,'%f'); + +filename=strcat(pre,'net_figure_new.txt'); + +drawFigureM(nnodes,bnet,labels,filename,cases,select_var_new,select_var_data_new); + +%quit force; +%marginal_nodes(engine,2) +%marginal_nodes(engine,3) +%marginal_nodes(engine,4) +%marginal_nodes(engine,5) +%evidence{1}=2; +%[engine,loglik]=enter_evidence(engine,evidence) +%marginal_nodes(engine,1) +%marginal_nodes(engine,2) +%marginal_nodes(engine,3) +%marginal_nodes(engine,4) +%marginal_nodes(engine,5) +%evidence{2}=0.6; +%evidence{1}=[]; +%[engine,loglik]=enter_evidence(engine,evidence); +%marginal_nodes(engine,3); +%marginal_nodes(engine,4); +%marginal_nodes(engine,5); +end \ No newline at end of file diff --git a/BNW_parameter_learning/checkDiscreteNodes.m b/BNW_parameter_learning/checkDiscreteNodes.m new file mode 100644 index 00000000..7b2a695f --- /dev/null +++ b/BNW_parameter_learning/checkDiscreteNodes.m @@ -0,0 +1,37 @@ +function [ ] = checkDiscreteNodes( bnet, cases) + %checkDiscreteNodes Checks if states of discrete nodes are be integers from 1 to M + % where M is the number of states of the node. (M should be the same as + % node_sizes in the bnet). + % + %Input: + % bnet: BNT bnet + % cases: cell array of data + % +% +node_sizes = bnet.node_sizes; +dnodes = bnet.dnodes; +ndisc = size(dnodes,2); +ncases = size(cases,2); + +%check to see that all data for discrete nodes are integers +for i = 1:ndisc + inode = dnodes(i); + data = cases(inode,:); + isize = node_sizes(inode); + states = zeros(1,isize); + for j = 1:isize + states(j) = j; + end + for j = 1:ncases + k = int64(data{j}); + if ~any(k==states) + error(['Discrete nodes must be integers from 1 to the number of states']); + end + end +end + + +end + + + diff --git a/BNW_parameter_learning/checkStructure.m b/BNW_parameter_learning/checkStructure.m new file mode 100644 index 00000000..fc72e4b7 --- /dev/null +++ b/BNW_parameter_learning/checkStructure.m @@ -0,0 +1,78 @@ +function [ labels, cases, dag, node_sizes, ord_flag ] = checkStructure(labels, cases, dag, node_sizes) + %checkStructure Check to see if nodes are sorted correctly. They must be + % in topological order (i.e., parents before children) before parameter + % learning can take place. + % + %Input and output have the same meaning. The output has just been + %topologically ordered. + % labels = cell array with the names of the nodes. + % cases = cell array with the data. + % dag = matrix with the strucutre of the network. + % node_sizes = vector with the size of each node. + +%make connections array +%count how big you need the connections array to be +nnodes = size(dag,1); +narcs = 0; +for i = 1:nnodes + for j = 1:nnodes + if dag(i,j) == 1 + narcs = narcs + 1; + end + end +end +%fill connections array with label names +connections = cell(narcs,2); +ncount = 0; +for i = 1:nnodes + for j = 1:nnodes + if dag(i,j) == 1 + ncount = ncount + 1; + connections{ncount,1} = labels{i}; + connections{ncount,2} = labels{j}; + end + end +end + +%get topologically sorted dag and labels +[new_dag, new_labels] = mk_adj_mat(connections, labels, 1); + +%check to see if order changed +ord_flag = 0; +for i = 1:nnodes + if ~strcmp(new_labels{i},labels{i}) + ord_flag = 1; + end +end + +if ord_flag + %get new ordering of nodes + order = cell(1,nnodes); + for i = 1:nnodes + for j = 1:nnodes + if strcmp(new_labels{j},labels{i}) + order{i} = j; + end + end + end + + %reorder cases and node_sizes + new_cases = cell(size(cases)); + for i = 1:nnodes + new_cases(order{i},:) = cases(i,:); + end + new_node_sizes = zeros(1,nnodes); + for i = 1:nnodes + new_node_sizes(order{i}) = node_sizes(i); + end + + + dag = new_dag; + cases = new_cases; + node_sizes = new_node_sizes; + labels = new_labels; +end + +end +%end checkStructure.m + diff --git a/BNW_parameter_learning/drawFigure.m b/BNW_parameter_learning/drawFigure.m new file mode 100644 index 00000000..a5de0f2d --- /dev/null +++ b/BNW_parameter_learning/drawFigure.m @@ -0,0 +1,383 @@ +function [] = drawFigure(nnodes,bnet,labels,filename,cases,selectvar,selectdata) +%drawFigure writes the parameters and data that are needed to draw the +%structure of a Bayesian network. + +if nargin < 6, + drawFigureNoEv(nnodes,bnet,labels,filename,cases); +else + drawFigureEv(nnodes,bnet,labels,filename,cases,selectvar,selectdata); +end; + +end + + + +function [] = drawFigureEv(nnodes,bnet,labels,filename,cases,selectvar,selectdata) +%Function to use if there is no entered evidence. +% +% +%Before each printed line, I will have a line that starts with %%% +% that describes what will be on that line + +%Create an empty evidence cell array. + +%val=cases; +%for i = 1:nnodes +% val(i,1)=val(i,2); + +%end + +A=cell2mat(cases'); +Amax=max(A); +Amin=min(A); + + +evidence = cell(1,nnodes); +engine = jtree_inf_engine(bnet); + +evidence{selectvar}=selectdata; + +[engine,loglik]=enter_evidence(engine,evidence); + +%Open the file, and write the nodes to a file. +fileID = fopen(filename,'w'); + +%%%%Evidence node +fprintf(fileID,'%i\n',selectvar); +%%% The number of nodes +fprintf(fileID,'%i\n',nnodes); +%Get canvas size +labels_temp = cellstr(labels); +[x,y] = make_layout(bnet.dag); + +x = x - min(x); +y = 1 - y; +y = y - min(y); + +[x_dim,y_dim] = canvasSize(nnodes,x,y); + +%%% The dimensions of the canvas for the javascript code +fprintf(fileID,'%i\t%i\t\n',x_dim,y_dim) + +x = x*x_dim; +y = y*y_dim; +for i = 1:nnodes, +%%% The name and X- and Y-positions of each node + fprintf(fileID,'%s\t%i\t%i\n',labels{i},round(x(i)),round(y(i))); +end + +%Get the number of parents and children for each node. +num_par = zeros(1,nnodes); +%For parents, sum down columns +for i = 1:nnodes, + for j = 1:nnodes, + if bnet.dag(j,i) == 1, + num_par(i) = num_par(i) + 1; + end + end +end +num_child = zeros(1,nnodes); +for i = 1:nnodes, + for j = 1:nnodes, + if bnet.dag(i,j) == 1, + num_child(i) = num_child(i) + 1; + end + end +end + + +for i = 1:nnodes, + %%% The name and type of each node (1=continuous, the number of states + %%% if it is discrete + fprintf(fileID,'%s\t%i\n',labels{i},bnet.node_sizes(i)); + %%% The size of the node, I am going to keep them + %%% 250(width) by 150(height) for now + %Could modify this to change the width based on the length of the node + %name + fprintf(fileID,'%i\t%i\n',250,150); + %%% The number of parents of the node, and the parents + if num_par(i) == 0; + %%% If no parents: + fprintf(fileID,'%i\n',num_par(i)); + else + parents = zeros(1,num_par(i)); + k = 1; + for j = 1:nnodes, + if bnet.dag(j,i) == 1, + parents(1,k) = j; + k = k + 1; + end + end + format = '%i\t'; + for j = 1:num_par(i)-1, + format = strcat(format,'%i\t'); + end + format = strcat(format,'%i\n'); + %%%If there are parents: + fprintf(fileID,format,num_par(i),parents(1,:)); + end + + + %%% The number of children of the node, and the children + if num_child(i) == 0; + %%% If no children: + fprintf(fileID,'%i\n',num_child(i)); + else + children = zeros(1,num_child(i)); + k = 1; + for j = 1:nnodes, + if bnet.dag(i,j) == 1, + children(1,k) = j; + k = k + 1; + end + end + format = '%i\t'; + for j = 1:num_child(i)-1, + format = strcat(format,'%i\t'); + end + format = strcat(format,'%i\n'); + %%%If there are parents: + fprintf(fileID,format,num_child(i),children(1,:)); + end + + predict = marginal_nodes(engine,i); + if isempty(evidence{i}) + if bnet.node_sizes(i) ~= 1, + for j = 1:bnet.node_sizes(i), + %%%For discrete nodes, the state and the percent of that state + fprintf(fileID,'%i\t%6.4f\n',j,predict.T(j)); + end; + else + + [x_vals,y_vals] = calcGaussian(predict.mu,predict.Sigma,Amax(i),Amin(i)); + %%%For continuous nodes, print x and the pdf of a normal curve. + for j = 1:101, + fprintf(fileID,'%6.4f\t%6.4f\n',x_vals(j,1),y_vals(j,1)); + end; + end; + else + fprintf(fileID,'%6.4f\t%6.4f\n',selectdata,1); + end + +end +%fprintf(fileID,'%s\t %\n',labels_temp{:}); + + +fclose(fileID); + +end + + + + + + +function [] = drawFigureNoEv(nnodes,bnet,labels,filename,cases) +%Function to use if there is no entered evidence. +% +% +%Before each printed line, I will have a line that starts with %%% +% that describes what will be on that line +A=cell2mat(cases'); +Amax=max(A); +Amin=min(A); + +%Create an empty evidence cell array. +evidence = cell(1,nnodes); +engine = jtree_inf_engine(bnet); +[engine,loglik] = enter_evidence(engine,evidence); + +%Open the file, and write the nodes to a file. +fileID = fopen(filename,'w'); +%%% The number of nodes +fprintf(fileID,'%i\n',nnodes); + +%Get canvas size + +labels_temp = cellstr(labels); +[x,y] = make_layout(bnet.dag); +%[x,y] = layout_dag(bnet.dag); + + +x = x - min(x); +y = 1 - y; +y = y - min(y); + +[x_dim,y_dim] = canvasSize(nnodes,x,y); + +%%% The dimensions of the canvas for the javascript code +fprintf(fileID,'%i\t%i\t\n',x_dim,y_dim) + +x = x*x_dim; +y = y*y_dim; +for i = 1:nnodes, +%%% The name and X- and Y-positions of each node + fprintf(fileID,'%s\t%i\t%i\n',labels{i},round(x(i)),round(y(i))); +end + +%Get the number of parents and children for each node. +num_par = zeros(1,nnodes); +%For parents, sum down columns +for i = 1:nnodes, + for j = 1:nnodes, + if bnet.dag(j,i) == 1, + num_par(i) = num_par(i) + 1; + end + end +end +num_child = zeros(1,nnodes); +for i = 1:nnodes, + for j = 1:nnodes, + if bnet.dag(i,j) == 1, + num_child(i) = num_child(i) + 1; + end + end +end + + +for i = 1:nnodes, + %%% The name and type of each node (1=continuous, the number of states + %%% if it is discrete + fprintf(fileID,'%s\t%i\n',labels{i},bnet.node_sizes(i)); + %%% The size of the node, I am going to keep them + %%% 250(width) by 150(height) for now + %Could modify this to change the width based on the length of the node + %name + fprintf(fileID,'%i\t%i\n',250,150); + %%% The number of parents of the node, and the parents + if num_par(i) == 0; + %%% If no parents: + fprintf(fileID,'%i\n',num_par(i)); + else + parents = zeros(1,num_par(i)); + k = 1; + for j = 1:nnodes, + if bnet.dag(j,i) == 1, + parents(1,k) = j; + k = k + 1; + end + end + format = '%i\t'; + for j = 1:num_par(i)-1, + format = strcat(format,'%i\t'); + end + format = strcat(format,'%i\n'); + %%%If there are parents: + fprintf(fileID,format,num_par(i),parents(1,:)); + end + + + %%% The number of children of the node, and the children + if num_child(i) == 0; + %%% If no children: + fprintf(fileID,'%i\n',num_child(i)); + else + children = zeros(1,num_child(i)); + k = 1; + for j = 1:nnodes, + if bnet.dag(i,j) == 1, + children(1,k) = j; + k = k + 1; + end + end + format = '%i\t'; + for j = 1:num_child(i)-1, + format = strcat(format,'%i\t'); + end + format = strcat(format,'%i\n'); + %%%If there are parents: + fprintf(fileID,format,num_child(i),children(1,:)); + end + + predict = marginal_nodes(engine,i); + if bnet.node_sizes(i) ~= 1, + for j = 1:bnet.node_sizes(i), + %%%For discrete nodes, the state and the percent of that state + fprintf(fileID,'%i\t%6.4f\n',j,predict.T(j)); + end; + else + %cases(i) + % MAX(cases(i)) + % MIN(cases(i)) + [x_vals,y_vals] = calcGaussian(predict.mu,predict.Sigma,Amax(i),Amin(i)); + %%%For continuous nodes, print x and the pdf of a normal curve. + for j = 1:101, + fprintf(fileID,'%6.4f\t%6.4f\n',x_vals(j,1),y_vals(j,1)); + end; + end; +end +%fprintf(fileID,'%s\t %\n',labels_temp{:}); + + +fclose(fileID); + +end + + +function [x_dim, y_dim] = canvasSize(nnodes,x,y) +%canvasSize Function to calculate the size of the canvas to +% build the network structure + + +%I am going to assume that the node size will be +% height = 150, width = 250 +% so there will be a node spacing of +% 200 (in y-dim) and 300 (in x-dim). +y_space = 200; +x_space = 300; + +%Set default minimum x and y dimensions +x_dim = 1200; +y_dim = 1200; + +%get unique y values +y_unique = unique(y); +size_y = size(y_unique,2); +y_dim_temp = size_y*y_space; + +%get the maximum nodes in any layer +size_x = zeros(1,size_y); +for i = 1:size_y, + for j = 1:nnodes, + if y_unique(i) == y(j), + size_x(1,i) = size_x(1,i) + 1; + end; + end; +end; +size_x = max(size_x); +x_dim_temp = size_x*x_space; + +if x_dim_temp > x_dim, + x_dim = x_dim_temp; +end; + +if y_dim_temp > y_dim, + y_dim = y_dim_temp; +end; +end + +function [x_vals,y_vals] = calcGaussian(mu,Sigma,maxval,minval) +%Function to calculate 101 points of Gaussian function to use in plotting +% Gets the probability density of the mean value and 50 evenly spaced +% points up to 3Sigma below the mean and 50 evenly space points up to +% 3Sigma above the mean. +%maxval +%minval +x_vals = zeros(101,1); +y_vals = zeros(101,1); + +%x_vals(1,1) = mu - 3*Sigma; +x_vals(1,1) = minval - 1; +gap=((maxval+1)-(minval - 1))/100; +%x_vals(1,1) = 0;%mu - 3*Sigma; +for i = 1:100, + % x_vals(i+1,1) = x_vals(1,1) + i*6*Sigma/100; + x_vals(i+1,1) = x_vals(i,1) + gap; + %x_vals(i+1,1) = x_vals(i,1) + 1/100; +end + +for i = 1:101, + y_vals(i,1) = normpdf(x_vals(i,1),mu,Sigma); +end + +end diff --git a/BNW_parameter_learning/drawFigureM.m b/BNW_parameter_learning/drawFigureM.m new file mode 100644 index 00000000..bca223ce --- /dev/null +++ b/BNW_parameter_learning/drawFigureM.m @@ -0,0 +1,258 @@ +function [] = drawFigureM(nnodes,bnet,labels,filename,cases,selectvar,selectdata) +%drawFigure writes the parameters and data that are needed to draw the +%structure of a Bayesian network. + + +%Function to use if there is no entered evidence. +% +% +%Before each printed line, I will have a line that starts with %%% +% that describes what will be on that line + +%Create an empty evidence cell array. + +%val=cases; +%for i = 1:nnodes +% val(i,1)=val(i,2); + +%end + +fileID = fopen(filename,'w'); + + +A=cell2mat(cases'); +Amax=max(A); +Amin=min(A); + + +evidence = cell(1,nnodes); +engine = jtree_inf_engine(bnet); + +m = size(selectvar,1); + + +ev_dat = zeros(1,nnodes); +%For parents, sum down columns +for i = 1:m, + di=selectvar(i,1); + ev_dat(di)=selectdata(i,1); + + evidence{di}=ev_dat(di); + fprintf(fileID,'%i\t',di); +end +fprintf(fileID,'\n'); + +%ev_dat + +% select_var = selectvar(1,1) +% +% select_var_data = selectdata(1,1) +% +% +% evidence{select_var}=select_var_data; + +[engine,loglik]=enter_evidence(engine,evidence); + +%Open the file, and write the nodes to a file. + + +%%%%Evidence node + +%%% The number of nodes +fprintf(fileID,'%i\n',nnodes); +%Get canvas size +labels_temp = cellstr(labels); +[x,y] = make_layout(bnet.dag); + +x = x - min(x); +y = 1 - y; +y = y - min(y); + +[x_dim,y_dim] = canvasSize(nnodes,x,y); + +%%% The dimensions of the canvas for the javascript code +fprintf(fileID,'%i\t%i\t\n',x_dim,y_dim) + +x = x*x_dim; +y = y*y_dim; +for i = 1:nnodes, +%%% The name and X- and Y-positions of each node + fprintf(fileID,'%s\t%i\t%i\n',labels{i},round(x(i)),round(y(i))); +end + +%Get the number of parents and children for each node. +num_par = zeros(1,nnodes); +%For parents, sum down columns +for i = 1:nnodes, + for j = 1:nnodes, + if bnet.dag(j,i) == 1, + num_par(i) = num_par(i) + 1; + end + end +end +num_child = zeros(1,nnodes); +for i = 1:nnodes, + for j = 1:nnodes, + if bnet.dag(i,j) == 1, + num_child(i) = num_child(i) + 1; + end + end +end + + +for i = 1:nnodes, + %%% The name and type of each node (1=continuous, the number of states + %%% if it is discrete + fprintf(fileID,'%s\t%i\n',labels{i},bnet.node_sizes(i)); + %%% The size of the node, I am going to keep them + %%% 250(width) by 150(height) for now + %Could modify this to change the width based on the length of the node + %name + fprintf(fileID,'%i\t%i\n',250,150); + %%% The number of parents of the node, and the parents + if num_par(i) == 0; + %%% If no parents: + fprintf(fileID,'%i\n',num_par(i)); + else + parents = zeros(1,num_par(i)); + k = 1; + for j = 1:nnodes, + if bnet.dag(j,i) == 1, + parents(1,k) = j; + k = k + 1; + end + end + format = '%i\t'; + for j = 1:num_par(i)-1, + format = strcat(format,'%i\t'); + end + format = strcat(format,'%i\n'); + %%%If there are parents: + fprintf(fileID,format,num_par(i),parents(1,:)); + end + + + %%% The number of children of the node, and the children + if num_child(i) == 0; + %%% If no children: + fprintf(fileID,'%i\n',num_child(i)); + else + children = zeros(1,num_child(i)); + k = 1; + for j = 1:nnodes, + if bnet.dag(i,j) == 1, + children(1,k) = j; + k = k + 1; + end + end + format = '%i\t'; + for j = 1:num_child(i)-1, + format = strcat(format,'%i\t'); + end + format = strcat(format,'%i\n'); + %%%If there are parents: + fprintf(fileID,format,num_child(i),children(1,:)); + end + + predict = marginal_nodes(engine,i); + if isempty(evidence{i}) + if bnet.node_sizes(i) ~= 1, + for j = 1:bnet.node_sizes(i), + %%%For discrete nodes, the state and the percent of that state + fprintf(fileID,'%i\t%6.4f\n',j,predict.T(j)); + end; + else + + [x_vals,y_vals] = calcGaussian(predict.mu,predict.Sigma,Amax(i),Amin(i)); + %%%For continuous nodes, print x and the pdf of a normal curve. + for j = 1:101, + fprintf(fileID,'%6.4f\t%6.4f\n',x_vals(j,1),y_vals(j,1)); + end; + end; + else + fprintf(fileID,'%6.4f\t%6.4f\n',ev_dat(i),1); + end + +end +%fprintf(fileID,'%s\t %\n',labels_temp{:}); + + +fclose(fileID); + +end + + + + + + + + + +function [x_dim, y_dim] = canvasSize(nnodes,x,y) +%canvasSize Function to calculate the size of the canvas to +% build the network structure + + +%I am going to assume that the node size will be +% height = 150, width = 250 +% so there will be a node spacing of +% 200 (in y-dim) and 300 (in x-dim). +y_space = 200; +x_space = 300; + +%Set default minimum x and y dimensions +x_dim = 1200; +y_dim = 1200; + +%get unique y values +y_unique = unique(y); +size_y = size(y_unique,2); +y_dim_temp = size_y*y_space; + +%get the maximum nodes in any layer +size_x = zeros(1,size_y); +for i = 1:size_y, + for j = 1:nnodes, + if y_unique(i) == y(j), + size_x(1,i) = size_x(1,i) + 1; + end; + end; +end; +size_x = max(size_x); +x_dim_temp = size_x*x_space; + +if x_dim_temp > x_dim, + x_dim = x_dim_temp; +end; + +if y_dim_temp > y_dim, + y_dim = y_dim_temp; +end; +end + +function [x_vals,y_vals] = calcGaussian(mu,Sigma,maxval,minval) +%Function to calculate 101 points of Gaussian function to use in plotting +% Gets the probability density of the mean value and 50 evenly spaced +% points up to 3Sigma below the mean and 50 evenly space points up to +% 3Sigma above the mean. +%maxval +%minval +x_vals = zeros(101,1); +y_vals = zeros(101,1); + +%x_vals(1,1) = mu - 3*Sigma; +x_vals(1,1) = minval - 1; +gap=((maxval+1)-(minval - 1))/100; +%x_vals(1,1) = 0;%mu - 3*Sigma; +for i = 1:100, + % x_vals(i+1,1) = x_vals(1,1) + i*6*Sigma/100; + x_vals(i+1,1) = x_vals(i,1) + gap; + %x_vals(i+1,1) = x_vals(i,1) + 1/100; +end + +for i = 1:101, + y_vals(i,1) = normpdf(x_vals(i,1),mu,Sigma); +end + +end diff --git a/BNW_parameter_learning/getParams.m b/BNW_parameter_learning/getParams.m new file mode 100644 index 00000000..4840b38d --- /dev/null +++ b/BNW_parameter_learning/getParams.m @@ -0,0 +1,22 @@ +function [ bnet ] = getParams( bnet, cases ) +%getParams Code to initialize CPT and do parameter learning. +%This will be very basic for now. I can add more options later. + +dnodes = bnet.dnodes; +cnodes = bnet.cnodes; +nnodes = size(dnodes,2)+size(cnodes,2); + +%make dnodes tabular_CPT +for i = 1:size(dnodes,2) + bnet.CPD{dnodes(i)} = tabular_CPD(bnet,dnodes(i)); +end + +for i = 1:size(cnodes,2) + bnet.CPD{cnodes(i)} = gaussian_CPD(bnet,cnodes(i)); +end + +bnet = learn_params(bnet,cases); + + +end + diff --git a/BNW_parameter_learning/parameterLearning.m b/BNW_parameter_learning/parameterLearning.m new file mode 100644 index 00000000..d4b67c87 --- /dev/null +++ b/BNW_parameter_learning/parameterLearning.m @@ -0,0 +1,17 @@ +function [ bnet ] = parameterLearning( bnet,cases,engine_name ) +%parameterLearning Do parameter learning and inference + +%engine is an optional argument +if nargin < 3 + engine_name = 'jtree_inf_engine'; +end + + +%First do parameter learning with all the data +[bnet] = getParams(bnet,cases); + + + + +end + diff --git a/BNW_parameter_learning/readInput.m b/BNW_parameter_learning/readInput.m new file mode 100644 index 00000000..c2c16331 --- /dev/null +++ b/BNW_parameter_learning/readInput.m @@ -0,0 +1,70 @@ +function [ labels, cases, bnet, node_sizes, data,labelsold] = readInput( dfile, sfile, nnodes, std_flag ) + %readInput is to be used when reading in a network with a known structure + % + %Input: + % dfile = name of the file containing the data (required) + % sfile = name of the file containing the structure (required) + % nnodes = number of nodes in the network (required) + % std_flag = flag for whether or not to standardize the data. + % (optional-- Default is FALSE) + % + % See readInputData.m and readInputStructure.m for description of the + % format of the dfile and sfile, respectively. + % + %Output: + % labels = cell array with the names of the nodes. + % cases = cell array with the data. + % bnet = BNT bayesian network with the input structure. + +if nargin < 4 + std_flag = false(1); +end + + +% read in the file with the data +[labelsold,node_sizes,cases, data] = readInputData(dfile,nnodes); + + + + +% read in the file with the structure +[dag] = readInputStructure(sfile,labelsold); + + +% check the ordering of the nodes and reorder if necessary +[labels,cases,dag,node_sizes,ord_flag] = checkStructure(labelsold,cases,dag,node_sizes); +%draw_graph(dag,labels); +%if ord_flag == 1 +% fprintf(['Order of nodes was changed to agree with topological order\n']) +%end +%fprintf(['The structure of the network should be correctly displayed in a figure\n']) + +dcount = 0; +for i = 1:nnodes + if node_sizes(i) ~= 1 + dcount = dcount + 1; + end +end +discrete = zeros(1,dcount); +dcount = 0; +for i = 1:nnodes + if node_sizes(i) ~= 1 + dcount = dcount + 1; + discrete(dcount) = i; + end +end + +bnet = mk_bnet(dag,node_sizes,'discrete',discrete,'names',labels); + +%bnet.dag + +checkDiscreteNodes(bnet,cases); + +% standardize continuous data to have a mean = 0 and std = 1 +if (std_flag) + [cases] = standardizeData(labels,node_sizes,cases); +end + + +end +% end of readInput.m \ No newline at end of file diff --git a/BNW_parameter_learning/readInputData.m b/BNW_parameter_learning/readInputData.m new file mode 100644 index 00000000..2df158f9 --- /dev/null +++ b/BNW_parameter_learning/readInputData.m @@ -0,0 +1,75 @@ +function [ labels , node_sizes, cases, data] = readInputData( dfile , nnodes ) + % readColData reads data from a file containing data in columns + % that have text titles, and possibly other header text + % + % Input: + % dfile = name of the file containing the data.(required) + % nnodes = number of columns in the data file. (required) + % + % Function assumes the following format for the input file: + % 1) First line has labels for each of the nodes. There cannot + % be spaces in any node label. + % 2) The next line is the "node_sizes" of the nodes. If the + % nodes are discrete, this number will be equal to the number + % of states. If the nodes are continuous, they should be + % equal to 1. The function assumes that any nodes with + % node_size = 1 is continuous. + % 3) The rest of the file is numeric data. The data in the input + % data has the number of columns equal to the number of + % nodes in the network and the number of rows equal to + % the number of samples. + % + % + % Output: + % labels = cell array with node (column) labels. + % node_sizes = vector with the size of each node + % cases = cell array with the data. The cases array is transposed + % in comparison with the input data to agree with the format of + % cell data used in BNT. + +% open file for input, include error handling +fin = fopen(dfile,'r'); +if fin < 0 + error(['Could not open ',dfile,' for input']); +end + +% Read in first line to get the node labels. +labels = cell(1,nnodes); +buffer = fgetl(fin); %get header line as a string +for j=1:nnodes + [next,buffer] = strtok(buffer); + labels{j} = next; +end + +% Read in the data. Use the vetorized fscanf function to load all +% numerical values into one vector. Then reshape this vector into a +% matrix. + +data = fscanf(fin,'%f'); % Load the numerical values into one long vector + + + + +nd = length(data); % total number of data points +nr = nd/nnodes; % number of rows; check (next statement) to make sure +if nr ~= round(nd/nnodes) + fprintf(1,'\ndata: nrow = %f\tncol = %d\n',nr,nnodes); + fprintf(1,'number of data points = %d does not equal nrow*ncol\n',nd); + error('data is not rectangular') +end + +data = reshape(data,nnodes,nr)'; % have to transpose the reshaped array + + +node_sizes = zeros(1,nnodes); +for j = 1:nnodes + node_sizes(j) = data(1,j); +end + +nr = nr - 1; +data(1,:) = []; +cases = cell(nnodes,nr); +cases(:,:) = num2cell(data'); + +end +% end of readInputData.m \ No newline at end of file diff --git a/BNW_parameter_learning/readInputStructure.m b/BNW_parameter_learning/readInputStructure.m new file mode 100644 index 00000000..72c39f46 --- /dev/null +++ b/BNW_parameter_learning/readInputStructure.m @@ -0,0 +1,72 @@ +function [ dag ] = readInputStructure( sfile, labels ) +%readInputStructure Read in file with structure information + % + %Input: + % sfile = name of the file containing the data (required) + % labels = cell array with node labels. (required) + % nnodes = number of columns in the data file. (required) + % + % Function assumes the following format for the structure input file: + % 1) The first line has node labels. These must be the same as + % in the input data file. They cannot contain spaces. + % 2) The remainder of the file contains the structure of the dag. + % The structure of a graph is a N-by-N matrix, where N is the + % number of nodes. There are 1's in the matrix representing + % parent-child relationships. For each 1, the row indicates + % the parent and the column indicates the child. For + % example, a 1 in the (2,3) position of the matrix indicates + % that there is an arc pointing from node 2 to node 3. + % + % + % Output: + % dag = matrix with the structure. +% +% Read in first line of the structure file +% open file for input, include error handling +fin = fopen(sfile,'r'); +if fin < 0 + error(['Could not open ',sfile,' for input']); +end + +nnodes = size(labels,2); +% Read in first line to get the node labels. +labels_test = cell(1,nnodes); +buffer = fgetl(fin); %get header line as a string +for j=1:nnodes + [next,buffer] = strtok(buffer); + labels_test{j} = next; +end + +for j=1:nnodes + if labels_test{j} ~= labels{j} + fprintf(['Label of node ',j,' is not consistent in input and structure files']) + end +end + +data = fscanf(fin,'%f'); + +nd = length(data); % total number of data points +nr = nd/nnodes; % number of rows; check (next statement) to make sure +if nr ~= round(nd/nnodes) + fprintf(1,'\ndata: nrow = %f\tncol = %d\n',nr,nnodes); + fprintf(1,'number of data points = %d does not equal nrow*ncol\n',nd); + error('Structure file does not have the correct dimensions (1)') +end +% check to make sure that structure is square +if nr ~= nnodes + error('Structure file does not have the correct dimensions (2)') +end + +data = reshape(data,nnodes,nr)'; % have to transpose the reshaped array + + +dag = zeros(nnodes,nnodes); +for i = 1:size(data,1) + for j = 1:size(data,2) + dag(i,j) = data(i,j); + end +end + + +end +% end of readInputStructure.m diff --git a/BNW_parameter_learning/runBN_initial.m b/BNW_parameter_learning/runBN_initial.m new file mode 100644 index 00000000..c3f2a34b --- /dev/null +++ b/BNW_parameter_learning/runBN_initial.m @@ -0,0 +1,98 @@ +function runBN_initial(pre) +sfile=strcat(pre,'structure_input.txt'); +dfile=strcat(pre,'continuous_input.txt'); + +nnodefile=strcat(pre,'nnode.txt'); +fnnode = fopen(nnodefile,'r'); +nnodes = fscanf(fnnode,'%d'); + + +mapfilename=strcat(pre,'mapdata.txt'); +mapvalfilename=strcat(pre,'map.txt'); + +mapfile = fopen(mapfilename,'w'); + +mapval = fopen(mapvalfilename,'w'); + + +%nnodes=5; +Std_flag=true; +[labels,cases,bnet,node_sizes,data,labelsold]=readInput(dfile,sfile,nnodes,Std_flag); +s = std(data,0,1); +m=mean(data); + + +for i=1:nnodes + fprintf(mapval,'%s\t%d\t%f\t%f\n',labelsold{i},node_sizes(i),s(i),m(i)); +end + + +% for j=1:nnodes +% [next,buffer] = strtok(buffer); +% name{j}=next; +% for i=1:nnodes +% if strcmp(name{j},labels{i}) +% map{j}=i; +% fprintf(mapfile,'%d\t',i); +% end +% end +% end +%name +%labels +%map +fprintf(mapfile,'%s',labels{1}); +for i=2:nnodes + fprintf(mapfile,'\t%s',labels{i}); +end +fprintf(mapfile,'\n'); + +[bnet]=parameterLearning(bnet,cases); +%[predict_mean,predict_sd,q_sq]=looCrossValid(bnet,cases); +%engine=jtree_inf_engine(bnet); +%evidence=cell(1,nnodes); + +%varfile='var.txt'; +%fvar = fopen(varfile,'r'); +%select_var = fscanf(fvar,'%d'); +%select_var=map{select_var}; +%varfiled='vardata.txt'; +%fvard = fopen(varfiled,'r'); +%select_var_data = fscanf(fvard,'%f'); + +%evidence{select_var}=select_var_data; +%[engine,loglik]=enter_evidence(engine,evidence); + +%outdata='prediction.txt'; +%fout = fopen(outdata,'w'); + +%for ii = 1:nnodes + % i=map{ii}; + % data=marginal_nodes(engine,i); + % fprintf(fout,'%d\t%d\t%f\t%f\t%f\n',ii,data.domain,data.T,data.mu,data.Sigma); + %fprintf(1,'%d\n',i); +% end + +filename=strcat(pre,'net_figure.txt'); +drawFigure(nnodes,bnet,labels,filename,cases); + +%quit force; +%marginal_nodes(engine,2) +%marginal_nodes(engine,3) +%marginal_nodes(engine,4) +%marginal_nodes(engine,5) +%evidence{1}=2; +%[engine,loglik]=enter_evidence(engine,evidence) +%marginal_nodes(engine,1) +%marginal_nodes(engine,2) +%marginal_nodes(engine,3) +%marginal_nodes(engine,4) +%marginal_nodes(engine,5) +%evidence{2}=0.6; +%evidence{1}=[]; +%[engine,loglik]=enter_evidence(engine,evidence); +%marginal_nodes(engine,3); +%marginal_nodes(engine,4); +%marginal_nodes(engine,5); +fclose(mapval); +fclose(mapfile); +end \ No newline at end of file diff --git a/BNW_parameter_learning/standardizeData.m b/BNW_parameter_learning/standardizeData.m new file mode 100644 index 00000000..ba4ef5dd --- /dev/null +++ b/BNW_parameter_learning/standardizeData.m @@ -0,0 +1,25 @@ +function [ cases ] = standardizeData( labels, node_sizes, cases ) +%standardizeData standardizes continuous nodes so they have a mean = 0 +% and standard deviation = 1 +% Detailed explanation goes here + +nnodes = size(labels,2); + +%fprintf(['Standardizing data for continuous nodes\n']) +for i = 1:nnodes + if node_sizes(i) == 1 + temp = cell2num(cases(i,:)); + [temp] = standardize(temp); + cases(i,:) = num2cell(temp); + end +end + +%write standardized data to file +%fprintf(['Standardized data is written to file standardized_data.txt\n']) +%fout = 'standardized_data.txt'; +%txt = sprintf([repmat('%s\t',1,size(labels,2))],labels{:}); +%dlmwrite(fout,txt,''); +%dlmwrite(fout,cell2num(cases'),'-append','delimiter','\t'); + +end + |
