about summary refs log tree commit diff
path: root/sourcecodes/bnt-master/KPMtools
diff options
context:
space:
mode:
Diffstat (limited to 'sourcecodes/bnt-master/KPMtools')
-rw-r--r--sourcecodes/bnt-master/KPMtools/CVS/Entries176
-rw-r--r--sourcecodes/bnt-master/KPMtools/CVS/Repository1
-rw-r--r--sourcecodes/bnt-master/KPMtools/CVS/Root1
-rw-r--r--sourcecodes/bnt-master/KPMtools/README.txt3
-rw-r--r--sourcecodes/bnt-master/KPMtools/approx_unique.m41
-rw-r--r--sourcecodes/bnt-master/KPMtools/approxeq.m21
-rw-r--r--sourcecodes/bnt-master/KPMtools/argmax.m11
-rw-r--r--sourcecodes/bnt-master/KPMtools/argmin.m12
-rw-r--r--sourcecodes/bnt-master/KPMtools/asdemo.html690
-rw-r--r--sourcecodes/bnt-master/KPMtools/asdemo.m70
-rw-r--r--sourcecodes/bnt-master/KPMtools/asort.m376
-rw-r--r--sourcecodes/bnt-master/KPMtools/assertBNT.m10
-rw-r--r--sourcecodes/bnt-master/KPMtools/assignEdgeNums.m32
-rw-r--r--sourcecodes/bnt-master/KPMtools/assign_cols.m36
-rw-r--r--sourcecodes/bnt-master/KPMtools/axis_pct.m70
-rw-r--r--sourcecodes/bnt-master/KPMtools/bipartiteMatchingDemo.m112
-rw-r--r--sourcecodes/bnt-master/KPMtools/bipartiteMatchingDemoPlot.m24
-rw-r--r--sourcecodes/bnt-master/KPMtools/bipartiteMatchingHungarian.m90
-rw-r--r--sourcecodes/bnt-master/KPMtools/bipartiteMatchingIntProg.m69
-rw-r--r--sourcecodes/bnt-master/KPMtools/block.m15
-rw-r--r--sourcecodes/bnt-master/KPMtools/cell2matPad.m22
-rw-r--r--sourcecodes/bnt-master/KPMtools/cell2num.m57
-rw-r--r--sourcecodes/bnt-master/KPMtools/centeringMatrix.m8
-rw-r--r--sourcecodes/bnt-master/KPMtools/checkpsd.m15
-rw-r--r--sourcecodes/bnt-master/KPMtools/chi2inv.m36
-rw-r--r--sourcecodes/bnt-master/KPMtools/choose.m5
-rw-r--r--sourcecodes/bnt-master/KPMtools/collapse_mog.m22
-rw-r--r--sourcecodes/bnt-master/KPMtools/colmult.c62
-rw-r--r--sourcecodes/bnt-master/KPMtools/computeROC.m64
-rw-r--r--sourcecodes/bnt-master/KPMtools/compute_counts.m17
-rw-r--r--sourcecodes/bnt-master/KPMtools/conf2mahal.m62
-rw-r--r--sourcecodes/bnt-master/KPMtools/cross_entropy.m15
-rw-r--r--sourcecodes/bnt-master/KPMtools/dirKPM.m98
-rw-r--r--sourcecodes/bnt-master/KPMtools/div.m5
-rw-r--r--sourcecodes/bnt-master/KPMtools/draw_circle.m28
-rw-r--r--sourcecodes/bnt-master/KPMtools/draw_ellipse.m24
-rw-r--r--sourcecodes/bnt-master/KPMtools/draw_ellipse_axes.m19
-rw-r--r--sourcecodes/bnt-master/KPMtools/em_converged.m32
-rw-r--r--sourcecodes/bnt-master/KPMtools/entropy.m17
-rw-r--r--sourcecodes/bnt-master/KPMtools/exportfig.m991
-rw-r--r--sourcecodes/bnt-master/KPMtools/extend_domain_table.m24
-rw-r--r--sourcecodes/bnt-master/KPMtools/factorial.m9
-rw-r--r--sourcecodes/bnt-master/KPMtools/filepartsLast.m12
-rw-r--r--sourcecodes/bnt-master/KPMtools/find_equiv_posns.m24
-rw-r--r--sourcecodes/bnt-master/KPMtools/fullfileKPM.m6
-rw-r--r--sourcecodes/bnt-master/KPMtools/genpathKPM.m45
-rw-r--r--sourcecodes/bnt-master/KPMtools/hash_add.m19
-rw-r--r--sourcecodes/bnt-master/KPMtools/hash_del.m26
-rw-r--r--sourcecodes/bnt-master/KPMtools/hash_lookup.m34
-rw-r--r--sourcecodes/bnt-master/KPMtools/hsvKPM.m7
-rw-r--r--sourcecodes/bnt-master/KPMtools/hungarian.m464
-rw-r--r--sourcecodes/bnt-master/KPMtools/image_rgb.m36
-rw-r--r--sourcecodes/bnt-master/KPMtools/imresizeAspect.m44
-rw-r--r--sourcecodes/bnt-master/KPMtools/ind2subv.m22
-rw-r--r--sourcecodes/bnt-master/KPMtools/ind2subvKPM.c176
-rw-r--r--sourcecodes/bnt-master/KPMtools/ind2subvKPM.m57
-rw-r--r--sourcecodes/bnt-master/KPMtools/ind2subvMinka.m23
-rw-r--r--sourcecodes/bnt-master/KPMtools/ind2subvTest.m10
-rw-r--r--sourcecodes/bnt-master/KPMtools/initFigures.m48
-rw-r--r--sourcecodes/bnt-master/KPMtools/installC_KPMtools.m9
-rw-r--r--sourcecodes/bnt-master/KPMtools/is_psd.m11
-rw-r--r--sourcecodes/bnt-master/KPMtools/is_stochastic.m5
-rw-r--r--sourcecodes/bnt-master/KPMtools/isemptycell.m16
-rw-r--r--sourcecodes/bnt-master/KPMtools/isequalKPM.m7
-rw-r--r--sourcecodes/bnt-master/KPMtools/isposdef.m9
-rw-r--r--sourcecodes/bnt-master/KPMtools/isscalarBNT.m5
-rw-r--r--sourcecodes/bnt-master/KPMtools/isvectorBNT.m9
-rw-r--r--sourcecodes/bnt-master/KPMtools/junk.c67
-rw-r--r--sourcecodes/bnt-master/KPMtools/loadcell.m153
-rw-r--r--sourcecodes/bnt-master/KPMtools/logb.m5
-rw-r--r--sourcecodes/bnt-master/KPMtools/logdet.m8
-rw-r--r--sourcecodes/bnt-master/KPMtools/logsum.m28
-rw-r--r--sourcecodes/bnt-master/KPMtools/logsum_simple.m23
-rw-r--r--sourcecodes/bnt-master/KPMtools/logsum_test.m6
-rw-r--r--sourcecodes/bnt-master/KPMtools/logsumexp.m24
-rw-r--r--sourcecodes/bnt-master/KPMtools/logsumexpv.m15
-rw-r--r--sourcecodes/bnt-master/KPMtools/mahal2conf.m60
-rw-r--r--sourcecodes/bnt-master/KPMtools/marg_table.m27
-rw-r--r--sourcecodes/bnt-master/KPMtools/marginalize_table.m50
-rw-r--r--sourcecodes/bnt-master/KPMtools/matprint.m36
-rw-r--r--sourcecodes/bnt-master/KPMtools/max_mult.c46
-rw-r--r--sourcecodes/bnt-master/KPMtools/max_mult.m21
-rw-r--r--sourcecodes/bnt-master/KPMtools/mexutil.c43
-rw-r--r--sourcecodes/bnt-master/KPMtools/mexutil.h8
-rw-r--r--sourcecodes/bnt-master/KPMtools/mk_multi_index.m23
-rw-r--r--sourcecodes/bnt-master/KPMtools/mk_stochastic.m27
-rw-r--r--sourcecodes/bnt-master/KPMtools/mkdirKPM.m24
-rw-r--r--sourcecodes/bnt-master/KPMtools/montageKPM.m102
-rw-r--r--sourcecodes/bnt-master/KPMtools/montageKPM2.m69
-rw-r--r--sourcecodes/bnt-master/KPMtools/montageKPM3.m5
-rw-r--r--sourcecodes/bnt-master/KPMtools/mult_by_table.m7
-rw-r--r--sourcecodes/bnt-master/KPMtools/myintersect.m28
-rw-r--r--sourcecodes/bnt-master/KPMtools/myismember.m18
-rw-r--r--sourcecodes/bnt-master/KPMtools/myismember.m~17
-rw-r--r--sourcecodes/bnt-master/KPMtools/myones.m11
-rw-r--r--sourcecodes/bnt-master/KPMtools/myplot.m7
-rw-r--r--sourcecodes/bnt-master/KPMtools/myrand.m12
-rw-r--r--sourcecodes/bnt-master/KPMtools/myrepmat.m9
-rw-r--r--sourcecodes/bnt-master/KPMtools/myreshape.m11
-rw-r--r--sourcecodes/bnt-master/KPMtools/mysetdiff.m19
-rw-r--r--sourcecodes/bnt-master/KPMtools/mysize.m16
-rw-r--r--sourcecodes/bnt-master/KPMtools/mysubset.m11
-rw-r--r--sourcecodes/bnt-master/KPMtools/mysymsetdiff.m29
-rw-r--r--sourcecodes/bnt-master/KPMtools/myunion.m29
-rw-r--r--sourcecodes/bnt-master/KPMtools/nchoose2.m35
-rw-r--r--sourcecodes/bnt-master/KPMtools/ncols.m4
-rw-r--r--sourcecodes/bnt-master/KPMtools/nonmaxsup.m42
-rw-r--r--sourcecodes/bnt-master/KPMtools/normalise.m34
-rw-r--r--sourcecodes/bnt-master/KPMtools/normaliseC.c29
-rw-r--r--sourcecodes/bnt-master/KPMtools/normaliseC.dllbin0 -> 6144 bytes
-rw-r--r--sourcecodes/bnt-master/KPMtools/normalize.m34
-rw-r--r--sourcecodes/bnt-master/KPMtools/nrows.m4
-rw-r--r--sourcecodes/bnt-master/KPMtools/num2strcell.m16
-rw-r--r--sourcecodes/bnt-master/KPMtools/optimalMatching.m90
-rw-r--r--sourcecodes/bnt-master/KPMtools/optimalMatchingTest.m18
-rw-r--r--sourcecodes/bnt-master/KPMtools/partitionData.m25
-rw-r--r--sourcecodes/bnt-master/KPMtools/partition_matrix_vec.m21
-rw-r--r--sourcecodes/bnt-master/KPMtools/pca_kpm.m32
-rw-r--r--sourcecodes/bnt-master/KPMtools/pca_netlab.m42
-rw-r--r--sourcecodes/bnt-master/KPMtools/pick.m9
-rw-r--r--sourcecodes/bnt-master/KPMtools/plotBox.m22
-rw-r--r--sourcecodes/bnt-master/KPMtools/plotColors.m10
-rw-r--r--sourcecodes/bnt-master/KPMtools/plotROC.m26
-rw-r--r--sourcecodes/bnt-master/KPMtools/plotROCkpm.m69
-rw-r--r--sourcecodes/bnt-master/KPMtools/plot_axis_thru_origin.m3
-rw-r--r--sourcecodes/bnt-master/KPMtools/plot_ellipse.m19
-rw-r--r--sourcecodes/bnt-master/KPMtools/plot_matrix.m48
-rw-r--r--sourcecodes/bnt-master/KPMtools/plot_polygon.m23
-rw-r--r--sourcecodes/bnt-master/KPMtools/plotcov2.m86
-rw-r--r--sourcecodes/bnt-master/KPMtools/plotcov2New.m119
-rw-r--r--sourcecodes/bnt-master/KPMtools/plotcov3.m109
-rw-r--r--sourcecodes/bnt-master/KPMtools/plotgauss1d.m9
-rw-r--r--sourcecodes/bnt-master/KPMtools/plotgauss2d.m130
-rw-r--r--sourcecodes/bnt-master/KPMtools/plotgauss2d_old.m40
-rw-r--r--sourcecodes/bnt-master/KPMtools/polygon_area.m22
-rw-r--r--sourcecodes/bnt-master/KPMtools/polygon_centroid.m79
-rw-r--r--sourcecodes/bnt-master/KPMtools/polygon_intersect.m60
-rw-r--r--sourcecodes/bnt-master/KPMtools/previewfig.m49
-rw-r--r--sourcecodes/bnt-master/KPMtools/process_options.m132
-rw-r--r--sourcecodes/bnt-master/KPMtools/rand_psd.m13
-rw-r--r--sourcecodes/bnt-master/KPMtools/rectintC.m22
-rw-r--r--sourcecodes/bnt-master/KPMtools/rectintLoopC.c71
-rw-r--r--sourcecodes/bnt-master/KPMtools/rectintLoopC.dllbin0 -> 20480 bytes
-rw-r--r--sourcecodes/bnt-master/KPMtools/rectintSparse.m59
-rw-r--r--sourcecodes/bnt-master/KPMtools/rectintSparseC.m32
-rw-r--r--sourcecodes/bnt-master/KPMtools/rectintSparseLoopC.c147
-rw-r--r--sourcecodes/bnt-master/KPMtools/rectintSparseLoopC.dllbin0 -> 8192 bytes
-rw-r--r--sourcecodes/bnt-master/KPMtools/repmatC.c149
-rw-r--r--sourcecodes/bnt-master/KPMtools/repmatC.dllbin0 -> 7680 bytes
-rw-r--r--sourcecodes/bnt-master/KPMtools/rgb2grayKPM.m11
-rw-r--r--sourcecodes/bnt-master/KPMtools/rnd_partition.m13
-rw-r--r--sourcecodes/bnt-master/KPMtools/rotate_xlabel.m37
-rw-r--r--sourcecodes/bnt-master/KPMtools/safeStr.m5
-rw-r--r--sourcecodes/bnt-master/KPMtools/sampleUniformInts.m6
-rw-r--r--sourcecodes/bnt-master/KPMtools/sample_discrete.m40
-rw-r--r--sourcecodes/bnt-master/KPMtools/set_xtick_label.m51
-rw-r--r--sourcecodes/bnt-master/KPMtools/set_xtick_label_demo.m52
-rw-r--r--sourcecodes/bnt-master/KPMtools/setdiag.m21
-rw-r--r--sourcecodes/bnt-master/KPMtools/softeye.m11
-rw-r--r--sourcecodes/bnt-master/KPMtools/sort_evec.m22
-rw-r--r--sourcecodes/bnt-master/KPMtools/splitLongSeqIntoManyShort.m16
-rw-r--r--sourcecodes/bnt-master/KPMtools/sprintf_intvec.m9
-rw-r--r--sourcecodes/bnt-master/KPMtools/sqdist.m29
-rw-r--r--sourcecodes/bnt-master/KPMtools/strmatch_multi.m30
-rw-r--r--sourcecodes/bnt-master/KPMtools/strmatch_substr.m28
-rw-r--r--sourcecodes/bnt-master/KPMtools/strsplit.m53
-rw-r--r--sourcecodes/bnt-master/KPMtools/subplot2.m17
-rw-r--r--sourcecodes/bnt-master/KPMtools/subplot3.m13
-rw-r--r--sourcecodes/bnt-master/KPMtools/subsets.m58
-rw-r--r--sourcecodes/bnt-master/KPMtools/subsets1.m45
-rw-r--r--sourcecodes/bnt-master/KPMtools/subsetsFixedSize.m45
-rw-r--r--sourcecodes/bnt-master/KPMtools/subv2ind.m17
-rw-r--r--sourcecodes/bnt-master/KPMtools/subv2indKPM.c89
-rw-r--r--sourcecodes/bnt-master/KPMtools/subv2indKPM.m66
-rw-r--r--sourcecodes/bnt-master/KPMtools/subv2indMinka.m17
-rw-r--r--sourcecodes/bnt-master/KPMtools/subv2indTest.m15
-rw-r--r--sourcecodes/bnt-master/KPMtools/sumv.m11
-rw-r--r--sourcecodes/bnt-master/KPMtools/suptitle.m105
-rw-r--r--sourcecodes/bnt-master/KPMtools/unaryEncoding.m16
-rw-r--r--sourcecodes/bnt-master/KPMtools/wrap.m7
-rw-r--r--sourcecodes/bnt-master/KPMtools/xticklabel_rotate90.m68
-rw-r--r--sourcecodes/bnt-master/KPMtools/zipload.m47
-rw-r--r--sourcecodes/bnt-master/KPMtools/zipsave.m42
183 files changed, 8805 insertions, 0 deletions
diff --git a/sourcecodes/bnt-master/KPMtools/CVS/Entries b/sourcecodes/bnt-master/KPMtools/CVS/Entries
new file mode 100644
index 00000000..041ea399
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/CVS/Entries
@@ -0,0 +1,176 @@
+/README.txt/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/approx_unique.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/approxeq.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/argmax.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/argmin.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/asdemo.html/1.1.1.1/Wed Mar 30 19:59:00 2005//
+/asdemo.m/1.1.1.1/Sun Mar 27 02:51:24 2005//
+/asort.m/1.1.1.1/Fri May 13 20:52:22 2005//
+/assert.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/assignEdgeNums.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/assign_cols.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/axis_pct.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/bipartiteMatchingDemo.m/1.1.1.1/Mon May  9 16:47:32 2005//
+/bipartiteMatchingDemoPlot.m/1.1.1.1/Mon May  9 04:45:10 2005//
+/bipartiteMatchingHungarian.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/bipartiteMatchingIntProg.m/1.1.1.1/Mon May  9 05:25:10 2005//
+/block.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/cell2matPad.m/1.1.1.1/Tue Jun 28 01:30:44 2005//
+/cell2num.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/centeringMatrix.m/1.1.1.1/Sun May  8 22:48:48 2005//
+/checkpsd.m/1.1.1.1/Fri Feb  7 02:25:30 2003//
+/chi2inv.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/choose.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/collapse_mog.m/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/colmult.c/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/colmult.mexglx/1.1.1.1/Tue Apr 26 02:30:30 2005//
+/computeROC.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/compute_counts.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/conf2mahal.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/cross_entropy.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/dirKPM.m/1.1.1.1/Fri May 13 20:52:22 2005//
+/div.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/draw_circle.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/draw_ellipse.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/draw_ellipse_axes.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/em_converged.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/entropy.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/exportfig.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/extend_domain_table.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/factorial.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/filepartsLast.m/1.1.1.1/Mon May 30 22:08:06 2005//
+/find_equiv_posns.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/fullfileKPM.m/1.1.1.1/Sat Aug 27 01:08:50 2005//
+/genpathKPM.m/1.1.1.1/Wed May 25 19:11:42 2005//
+/hash_add.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/hash_del.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/hash_lookup.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/hsvKPM.m/1.1.1.1/Mon May  2 20:19:00 2005//
+/hungarian.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/image_rgb.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/imresizeAspect.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/ind2subv.c/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/ind2subv.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/initFigures.m/1.1.1.1/Wed Jun  1 04:49:22 2005//
+/installC_KPMtools.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/is_psd.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/is_stochastic.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/isemptycell.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/isposdef.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/isscalar.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/isvector.m/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/junk.c/1.1.1.1/Tue Apr 26 02:30:32 2005//
+/loadcell.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/logb.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/logdet.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/logsum.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/logsum_simple.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/logsum_test.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/logsumexp.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/logsumexpv.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/mahal2conf.m/1.1.1.1/Wed Apr 27 17:58:32 2005//
+/marg_table.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/marginalize_table.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/matprint.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/max_mult.c/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/max_mult.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/mexutil.c/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/mexutil.h/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/mk_multi_index.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/mk_stochastic.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/mkdirKPM.m/1.1.1.1/Mon May  9 22:20:22 2005//
+/montageKPM.m/1.1.1.1/Wed Jun  1 19:39:54 2005//
+/montageKPM2.m/1.1.1.1/Wed Jul  6 19:32:54 2005//
+/montageKPM3.m/1.1.1.1/Tue Jun 28 01:35:44 2005//
+/mult_by_table.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/myintersect.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/myismember.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/myones.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/myplot.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/myrand.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/myrepmat.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/myreshape.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/mysetdiff.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/mysize.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/mysubset.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/mysymsetdiff.m/1.1.1.1/Tue Apr 26 02:30:34 2005//
+/myunion.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/nchoose2.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/ncols.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/nonmaxsup.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/normalise.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/normaliseC.c/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/normaliseC.dll/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/normalize.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/nrows.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/num2strcell.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/optimalMatching.m/1.1.1.1/Mon May  9 22:20:22 2005//
+/optimalMatchingTest.m/1.1.1.1/Mon May  9 22:20:22 2005//
+/partitionData.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/partition_matrix_vec.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/pca_kpm.m/1.1.1.1/Tue Sep 13 05:18:28 2005//
+/pca_netlab.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/pick.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plotBox.m/1.1.1.1/Mon May 30 06:01:56 2005//
+/plotColors.m/1.1.1.1/Thu May 26 01:31:22 2005//
+/plotROC.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plotROCkpm.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plot_axis_thru_origin.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plot_ellipse.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plot_matrix.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plot_polygon.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plotcov2.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plotcov2New.m/1.1.1.1/Mon Jul 11 19:07:28 2005//
+/plotcov3.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plotgauss1d.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plotgauss2d.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/plotgauss2d_old.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/polygon_area.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/polygon_centroid.m/1.1.1.1/Tue Apr 26 02:30:36 2005//
+/polygon_intersect.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/previewfig.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/process_options.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/rand_psd.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/rectintC.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/rectintLoopC.c/1.1.1.1/Sun Jun  5 18:46:40 2005//
+/rectintLoopC.dll/1.1.1.1/Sun Jun  5 18:46:40 2005//
+/rectintLoopC.mexglx/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/rectintSparse.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/rectintSparseC.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/rectintSparseLoopC.c/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/rectintSparseLoopC.dll/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/repmatC.c/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/repmatC.dll/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/repmatC.mexglx/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/rgb2grayKPM.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/rnd_partition.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/rotate_xlabel.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/safeStr.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/sampleUniformInts.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/sample_discrete.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/set_xtick_label.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/set_xtick_label_demo.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/setdiag.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/softeye.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/sort_evec.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/splitLongSeqIntoManyShort.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/sprintf_intvec.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/sqdist.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/strmatch_multi.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/strmatch_substr.m/1.1.1.1/Tue Apr 26 02:30:38 2005//
+/strsplit.m/1.1.1.1/Tue May  3 19:01:46 2005//
+/subplot2.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/subplot3.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/subsets.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/subsets1.m/1.1.1.1/Mon May  9 22:20:22 2005//
+/subsetsFixedSize.m/1.1.1.1/Mon May  9 02:55:36 2005//
+/subv2ind.c/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/subv2ind.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/sumv.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/suptitle.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/unaryEncoding.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/wrap.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/xticklabel_rotate90.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/zipload.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+/zipsave.m/1.1.1.1/Tue Apr 26 02:30:40 2005//
+D
diff --git a/sourcecodes/bnt-master/KPMtools/CVS/Repository b/sourcecodes/bnt-master/KPMtools/CVS/Repository
new file mode 100644
index 00000000..0b5b553e
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/CVS/Repository
@@ -0,0 +1 @@
+FullBNT/KPMtools
diff --git a/sourcecodes/bnt-master/KPMtools/CVS/Root b/sourcecodes/bnt-master/KPMtools/CVS/Root
new file mode 100644
index 00000000..f3bd14a6
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/CVS/Root
@@ -0,0 +1 @@
+:ext:nsaunier@bnt.cvs.sourceforge.net:/cvsroot/bnt
diff --git a/sourcecodes/bnt-master/KPMtools/README.txt b/sourcecodes/bnt-master/KPMtools/README.txt
new file mode 100644
index 00000000..fff044b0
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/README.txt
@@ -0,0 +1,3 @@
+KPMtools is a directory of miscellaneous matlab functions written by
+Kevin Patrick Murphy and various other people (see individual file headers).
+
diff --git a/sourcecodes/bnt-master/KPMtools/approx_unique.m b/sourcecodes/bnt-master/KPMtools/approx_unique.m
new file mode 100644
index 00000000..adb5bd07
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/approx_unique.m
@@ -0,0 +1,41 @@
+function [B, keep] = approx_unique(A, thresh, flag)
+% APPROX_UNIQUE Return elements of A that differ from the rest by less than thresh
+% B = approx_unique(A, thresh)
+% B = approx_unique(A, thresh, 'rows')
+
+keep = [];
+
+if nargin < 3 | isempty(flag)
+  A = sort(A)
+  B = A(1);
+  for i=2:length(A)
+    if ~approxeq(A(i), A(i-1), thresh)
+      B = [B A(i)];
+      keep = [keep i];
+    end
+  end
+else
+%   A = sortrows(A);
+%   B = A(1,:);
+%   for i=2:size(A,1)
+%     if ~approxeq(A(i,:), A(i-1,:), thresh)
+%       B = [B; A(i,:)];
+%       keep = [keep i];
+%     end
+%   end
+  B = [];
+  for i=1:size(A,1)
+    duplicate = 0;
+    for j=i+1:size(A,1)
+      if approxeq(A(i,:), A(j,:), thresh)
+	duplicate = 1;
+	break;
+      end
+    end
+    if ~duplicate    
+      B = [B; A(i,:)];
+      keep = [keep i];
+    end
+  end
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/approxeq.m b/sourcecodes/bnt-master/KPMtools/approxeq.m
new file mode 100644
index 00000000..559efc5e
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/approxeq.m
@@ -0,0 +1,21 @@
+function p = approxeq(a, b, tol, rel)
+% APPROXEQ Are a and b approximately equal (to within a specified tolerance)?
+% p = approxeq(a, b, thresh)
+% 'tol' defaults to 1e-3.
+% p(i) = 1 iff abs(a(i) - b(i)) < thresh
+%
+% p = approxeq(a, b, thresh, 1)
+% p(i) = 1 iff abs(a(i)-b(i))/abs(a(i)) < thresh
+
+if nargin < 3, tol = 1e-2; end
+if nargin < 4, rel = 0; end
+
+a = a(:);
+b = b(:);
+d = abs(a-b);
+if rel
+  p = ~any( (d ./ (abs(a)+eps)) > tol);
+else
+  p = ~any(d > tol);
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/argmax.m b/sourcecodes/bnt-master/KPMtools/argmax.m
new file mode 100644
index 00000000..1dcc1ecf
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/argmax.m
@@ -0,0 +1,11 @@
+function indices = argmax(v)
+% ARGMAX Return as a subscript vector the location of the largest element of a multidimensional array v.
+% indices = argmax(v)
+%
+% Returns the first maximum in the case of ties.
+% Example:
+% X = [2 8 4; 7 3 9];
+% argmax(X) = [2 3], i.e., row 2 column 3
+
+[m i] = max(v(:));
+indices = ind2subv(mysize(v), i);
diff --git a/sourcecodes/bnt-master/KPMtools/argmin.m b/sourcecodes/bnt-master/KPMtools/argmin.m
new file mode 100644
index 00000000..74dc276f
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/argmin.m
@@ -0,0 +1,12 @@
+function indices = argmin(v)
+% ARGMIN Return as a subscript vector the location of the smallest element of a multidimensional array v.
+% indices = argmin(v)
+%
+% Returns the first minimum in the case of ties.
+% Example:
+% X = [2 8 4; 7 3 9];
+% argmin(X) = [1 1], i.e., row 1 column 1
+
+[m i] = min(v(:));
+indices = ind2subv(mysize(v), i);
+%indices = ind2subv(size(v), i);
diff --git a/sourcecodes/bnt-master/KPMtools/asdemo.html b/sourcecodes/bnt-master/KPMtools/asdemo.html
new file mode 100644
index 00000000..f77c8660
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/asdemo.html
@@ -0,0 +1,690 @@
+<html xmlns:v="urn:schemas-microsoft-com:vml"
+xmlns:o="urn:schemas-microsoft-com:office:office"
+xmlns:w="urn:schemas-microsoft-com:office:word"
+xmlns:st1="urn:schemas-microsoft-com:office:smarttags"
+xmlns:mwsh="http://www.mathworks.com/namespace/mcode/v1/syntaxhighlight.dtd"
+xmlns="http://www.w3.org/TR/REC-html40">
+
+<head>
+<meta http-equiv=Content-Type content="text/html; charset=utf-8">
+<meta name=ProgId content=Word.Document>
+<meta name=Generator content="Microsoft Word 10">
+<meta name=Originator content="Microsoft Word 10">
+<link rel=File-List href="asdemo_files/filelist.xml">
+<title>asdemo</title>
+<o:SmartTagType namespaceuri="urn:schemas-microsoft-com:office:smarttags"
+ name="time"/>
+<o:SmartTagType namespaceuri="urn:schemas-microsoft-com:office:smarttags"
+ name="date"/>
+<o:SmartTagType namespaceuri="urn:schemas-microsoft-com:office:smarttags"
+ name="place"/>
+<!--[if gte mso 9]><xml>
+ <o:DocumentProperties>
+  <o:Author>Caroline Schwarz</o:Author>
+  <o:Template>Normal</o:Template>
+  <o:LastAuthor>us</o:LastAuthor>
+  <o:Revision>33</o:Revision>
+  <o:TotalTime>0</o:TotalTime>
+  <o:Created>2005-03-26T16:20:00Z</o:Created>
+  <o:LastSaved>2005-03-30T09:58:00Z</o:LastSaved>
+  <o:Pages>1</o:Pages>
+  <o:Words>1062</o:Words>
+  <o:Characters>6055</o:Characters>
+  <o:Company>office</o:Company>
+  <o:Lines>50</o:Lines>
+  <o:Paragraphs>14</o:Paragraphs>
+  <o:CharactersWithSpaces>7103</o:CharactersWithSpaces>
+  <o:Version>10.3501</o:Version>
+ </o:DocumentProperties>
+ <o:OfficeDocumentSettings>
+  <o:RelyOnVML/>
+  <o:AllowPNG/>
+  <o:TargetScreenSize>1280x1024</o:TargetScreenSize>
+ </o:OfficeDocumentSettings>
+</xml><![endif]--><!--[if gte mso 9]><xml>
+ <w:WordDocument>
+  <w:SpellingState>Clean</w:SpellingState>
+  <w:GrammarState>Clean</w:GrammarState>
+  <w:Compatibility>
+   <w:UseFELayout/>
+  </w:Compatibility>
+  <w:BrowserLevel>MicrosoftInternetExplorer4</w:BrowserLevel>
+ </w:WordDocument>
+</xml><![endif]--><!--[if !mso]><object
+ classid="clsid:38481807-CA0E-42D2-BF39-B33AF135CC4D" id=ieooui></object>
+<style>
+st1\:*{behavior:url(#ieooui) }
+</style>
+<![endif]-->
+<style>
+<!--p
+	{max-width: 600px;
+	width:expression(document.body.clientWidth > 620 ? "600px": "auto" );}
+h1
+	{max-width: 600px;
+	width:expression(document.body.clientWidth > 620 ? "600px": "auto" );}
+h2
+	{max-width: 600px;
+	width:expression(document.body.clientWidth > 620 ? "600px": "auto" );}
+div
+	{max-width: 600px;
+	width:expression(document.body.clientWidth > 620 ? "600px": "auto" );}
+
+ /* Font Definitions */
+ @font-face
+	{font-family:"MS Mincho";
+	panose-1:2 2 6 9 4 2 5 8 3 4;
+	mso-font-alt:"ï¼­ï¼³ 明æœ";
+	mso-font-charset:128;
+	mso-generic-font-family:modern;
+	mso-font-pitch:fixed;
+	mso-font-signature:-1610612033 1757936891 16 0 131231 0;}
+@font-face
+	{font-family:"\@MS Mincho";
+	panose-1:2 2 6 9 4 2 5 8 3 4;
+	mso-font-charset:128;
+	mso-generic-font-family:modern;
+	mso-font-pitch:fixed;
+	mso-font-signature:-1610612033 1757936891 16 0 131231 0;}
+ /* Style Definitions */
+ p.MsoNormal, li.MsoNormal, div.MsoNormal
+	{mso-style-parent:"";
+	margin:0cm;
+	margin-bottom:.0001pt;
+	mso-pagination:widow-orphan;
+	font-size:10.0pt;
+	font-family:Arial;
+	mso-fareast-font-family:"Times New Roman";
+	mso-believe-normal-left:yes;}
+h1
+	{mso-margin-top-alt:auto;
+	margin-right:0cm;
+	mso-margin-bottom-alt:auto;
+	margin-left:0cm;
+	mso-pagination:widow-orphan;
+	mso-outline-level:1;
+	font-size:24.0pt;
+	font-family:Arial;
+	mso-fareast-font-family:"MS Mincho";
+	color:#990000;
+	font-weight:bold;}
+h2
+	{mso-margin-top-alt:auto;
+	margin-right:0cm;
+	mso-margin-bottom-alt:auto;
+	margin-left:0cm;
+	mso-pagination:widow-orphan;
+	mso-outline-level:2;
+	font-size:13.5pt;
+	font-family:Arial;
+	mso-fareast-font-family:"MS Mincho";
+	color:#990000;
+	font-weight:bold;}
+p
+	{mso-margin-top-alt:auto;
+	margin-right:0cm;
+	mso-margin-bottom-alt:auto;
+	margin-left:0cm;
+	mso-pagination:widow-orphan;
+	font-size:10.0pt;
+	font-family:Arial;
+	mso-fareast-font-family:"Times New Roman";}
+pre
+	{margin:0cm;
+	margin-bottom:.0001pt;
+	mso-pagination:widow-orphan;
+	tab-stops:45.8pt 91.6pt 137.4pt 183.2pt 229.0pt 274.8pt 320.6pt 366.4pt 412.2pt 458.0pt 503.8pt 549.6pt 595.4pt 641.2pt 687.0pt 732.8pt;
+	font-size:10.0pt;
+	font-family:"Courier New";
+	mso-fareast-font-family:"Times New Roman";}
+p.footer, li.footer, div.footer
+	{mso-style-name:footer;
+	mso-margin-top-alt:auto;
+	margin-right:0cm;
+	mso-margin-bottom-alt:auto;
+	margin-left:0cm;
+	text-align:right;
+	mso-pagination:widow-orphan;
+	font-size:7.5pt;
+	font-family:Arial;
+	mso-fareast-font-family:"Times New Roman";
+	color:gray;
+	font-style:italic;}
+span.keyword
+	{mso-style-name:keyword;
+	color:blue;}
+span.comment
+	{mso-style-name:comment;
+	color:forestgreen;}
+span.string
+	{mso-style-name:string;
+	color:#A020F0;}
+span.untermstring
+	{mso-style-name:untermstring;
+	color:#B20000;}
+span.syscmd
+	{mso-style-name:syscmd;
+	color:#B28C00;}
+span.SpellE
+	{mso-style-name:"";
+	mso-spl-e:yes;}
+span.GramE
+	{mso-style-name:"";
+	mso-gram-e:yes;}
+@page Section1
+	{size:612.0pt 792.0pt;
+	margin:72.0pt 90.0pt 72.0pt 90.0pt;
+	mso-header-margin:36.0pt;
+	mso-footer-margin:36.0pt;
+	mso-paper-source:0;}
+div.Section1
+	{page:Section1;}
+-->
+</style>
+<!--[if gte mso 10]>
+<style>
+ /* Style Definitions */
+ table.MsoNormalTable
+	{mso-style-name:"Table Normal";
+	mso-tstyle-rowband-size:0;
+	mso-tstyle-colband-size:0;
+	mso-style-noshow:yes;
+	mso-style-parent:"";
+	mso-padding-alt:0cm 5.4pt 0cm 5.4pt;
+	mso-para-margin:0cm;
+	mso-para-margin-bottom:.0001pt;
+	mso-pagination:widow-orphan;
+	font-size:10.0pt;
+	font-family:"Times New Roman";}
+</style>
+<![endif]--><![if mso 9]>
+<style>
+p.MsoNormal
+	{margin-left:7.5pt;}
+</style>
+<![endif]><!--
+This HTML is auto-generated from an M-file.
+To make changes, update the M-file and republish this document.
+      -->
+<meta name=date content=2005-03-26>
+<meta name=m-file content=asdemo>
+<!--[if gte mso 9]><xml>
+ <o:shapedefaults v:ext="edit" spidmax="5122"/>
+</xml><![endif]--><!--[if gte mso 9]><xml>
+ <o:shapelayout v:ext="edit">
+  <o:idmap v:ext="edit" data="1"/>
+ </o:shapelayout></xml><![endif]-->
+</head>
+
+<body bgcolor=white lang=EN-US style='tab-interval:36.0pt;margin-left:7.5pt;
+margin-top:7.5pt;margin-right:7.5pt;margin-bottom:7.5pt'>
+
+<div class=Section1><pre style='margin-left:22.5pt'><span class=comment>% <b
+style='mso-bidi-font-weight:normal'>ASORT</b></span></pre><pre
+style='margin-left:22.5pt'><span class=comment>% a pedestrian <b
+style='mso-bidi-font-weight:normal'>NUMERICAL SORTER</b> of <b
+style='mso-bidi-font-weight:normal'>ALPHANUMERIC</b> data</span></pre><pre
+style='margin-left:22.5pt'><o:p>&nbsp;</o:p></pre><pre style='margin-left:22.5pt'><span
+class=comment>% - create some data</span></pre><pre style='margin-left:22.5pt'><b
+style='mso-bidi-font-weight:normal'><span style='mso-tab-count:2'>          </span>d = {<o:p></o:p></b></pre><pre
+style='margin-left:22.5pt'><span class=comment>%<span style='mso-tab-count:
+2'>         </span>strings with one valid alphanumeric number</span></pre><pre
+style='margin-left:22.5pt'><span class=comment>%<span style='mso-tab-count:
+2'>         </span>sorted <b style='mso-bidi-font-weight:normal'>numerically</b></span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'-<span class=SpellE><span class=GramE>inf</span></span>'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'<span class=GramE>x-3.2e4y</span>'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'<span class=GramE>f-1.4</span>'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'-.1'</span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=string>'+ <span
+class=GramE>.1d-2</span>'</span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=string>'.1'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'f.1'</span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=string>'f -+1.4'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'f.2'</span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=string>'f.3'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'f.10'</span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=string>'f.11'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'+<span class=SpellE>inf</span>'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=GramE><span class=string>' -</span></span><span class=SpellE><span
+class=string>nan</span></span><span class=string>'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'+ <span class=SpellE><span class=GramE>nan</span></span>'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'<span class=SpellE><span class=GramE>nan</span></span>'</span></pre><pre
+style='margin-left:22.5pt'><span class=comment>%<span style='mso-tab-count:
+2'>         </span>strings with many numbers or invalid/ambiguous numbers</span></pre><pre
+style='margin-left:22.5pt'><span class=comment>%<span style='mso-tab-count:
+2'>         </span>sorted in <span class=SpellE><span class=GramE><b
+style='mso-bidi-font-weight:normal'>ascii</b></span></span><b style='mso-bidi-font-weight:
+normal'> dictionary order</b></span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=GramE><span
+class=string>' <span class=SpellE>nan</span></span></span><span class=string> <span
+class=SpellE>nan</span>'</span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=string>'+ .1e-.2'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'-1 2'</span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=string>'Z12e12ez'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'<span class=SpellE><span class=GramE>inf</span></span> -<span
+class=SpellE>inf</span>'</span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=string>'s.3TT.4'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'z12e12ez'</span></pre><pre style='margin-left:22.5pt'><span
+class=comment>%<span style='mso-tab-count:2'>         </span>strings without numbers</span></pre><pre
+style='margin-left:22.5pt'><span class=comment>%<span style='mso-tab-count:
+2'>         </span>sorted in <span class=SpellE><span class=GramE><b
+style='mso-bidi-font-weight:normal'>ascii</b></span></span><b style='mso-bidi-font-weight:
+normal'> dictionary order</b></span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=string>' . .. '</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'.'</span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:3'>                  </span><span class=string>'...'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=GramE><span class=string>'.b a.'</span></span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'<span class=GramE>a</span> string'</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:3'>                  </span><span
+class=string>'a. .b'</span></pre><pre style='margin-left:22.5pt'><b
+style='mso-bidi-font-weight:normal'><span style='mso-tab-count:2'>          </span>};<o:p></o:p></b></pre><pre
+style='margin-left:22.5pt'><span class=comment>%<span style='mso-spacerun:yes'>   </span>... and scramble it...</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:2'>          </span><span
+class=GramE>rand(</span><span class=string>'seed'</span>,10);</pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:2'>          </span>d=<span
+class=GramE>d(</span><span class=SpellE>randperm</span>(<span class=SpellE>numel</span>(d)));</pre><pre
+style='margin-left:22.5pt'><o:p>&nbsp;</o:p></pre><pre style='margin-left:22.5pt'><span
+class=comment>% - run <b style='mso-bidi-font-weight:normal'>ASORT</b> with<o:p></o:p></span></pre><pre
+style='margin-left:22.5pt'><span class=comment>%<span style='mso-spacerun:yes'>   </span><b
+style='mso-bidi-font-weight:normal'>verbose output</b>:<span style='mso-tab-count:
+2'>              </span>&lt;-v&gt;</span></pre><pre style='margin-left:22.5pt'><span
+class=comment>%<span style='mso-spacerun:yes'>   </span><span class=GramE><b
+style='mso-bidi-font-weight:normal'>keep</b></span><b style='mso-bidi-font-weight:
+normal'> additional results</b>:<span style='mso-tab-count:1'>     </span>&lt;-d&gt;</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:2'>          </span>o=<span
+class=SpellE><span class=GramE>asort</span></span><span class=GramE>(</span>d,<span
+class=string>'-v'</span>,<span class=string>'-d'</span>);</pre><pre
+style='margin-left:22.5pt'><span class=comment>% - or</span></pre><pre
+style='margin-left:22.5pt'><span class=comment>%<span style='mso-tab-count:
+2'>         </span>p=<span class=SpellE><span class=GramE>asort</span></span><span
+class=GramE>(</span>char(d),</span><span class=string>'-v'</span>,<span
+class=string>'-d'</span>);</pre><pre style='margin-left:7.5pt'><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'INPUT'<span style='mso-spacerun:yes'>       </span>'ASCII SORT'<span style='mso-spacerun:yes'>    </span>'NUM SORT'<span style='mso-spacerun:yes'>             </span>'NUM READ'<span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'...'<span style='mso-spacerun:yes'>         </span><span
+class=SpellE><span class=GramE>'</span></span><span class=GramE> -</span><span
+class=SpellE>nan</span>'<span style='mso-spacerun:yes'>         </span>'--- NUMERICAL'<span style='mso-spacerun:yes'>        </span>'--- NUMBERS'<span style='mso-spacerun:yes'>      </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'+ .1e-.2'<span style='mso-spacerun:yes'>    </span><span
+class=GramE>' .</span> .. '<span style='mso-spacerun:yes'>        </span>'-<span
+class=SpellE><span class=GramE>inf</span></span>'<span style='mso-spacerun:yes'>         </span><span style='mso-spacerun:yes'>        </span>[<span style='mso-spacerun:yes'>             </span>-<span
+class=SpellE>Inf</span>]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'.1'<span style='mso-spacerun:yes'>          </span>' <span
+class=SpellE>nan</span> <span class=SpellE>nan</span>'<span style='mso-spacerun:yes'>      </span>'x-3.2e4y'<span style='mso-spacerun:yes'>             </span>[<span style='mso-spacerun:yes'>           </span>-32000]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'.b a.'<span style='mso-spacerun:yes'>       </span>'+ .1d-2'<span style='mso-spacerun:yes'>       </span>'f-1.4'<span style='mso-spacerun:yes'>                </span>[<span style='mso-spacerun:yes'>             </span>-1.4]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'-<span
+class=SpellE>inf</span>'<span style='mso-spacerun:yes'>        </span>'+ .1e-.2'<span style='mso-spacerun:yes'>      </span>'-.1'<span style='mso-spacerun:yes'>                  </span>[<span style='mso-spacerun:yes'>             </span>-0.1]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f.1'<span style='mso-spacerun:yes'>         </span>'+ <span
+class=SpellE><span class=GramE>nan</span></span>'<span style='mso-spacerun:yes'>         </span>'+ .1d-2'<span style='mso-spacerun:yes'>              </span>[<span style='mso-spacerun:yes'>            </span>0.001]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span class=GramE>' -</span><span
+class=SpellE>nan</span>'<span style='mso-spacerun:yes'>       </span>'+<span
+class=SpellE>inf</span>'<span style='mso-spacerun:yes'>          </span>'.1'<span style='mso-spacerun:yes'>                   </span>[<span style='mso-spacerun:yes'>              </span>0.1]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'-1 2'<span style='mso-spacerun:yes'>        </span>'-.1'<span style='mso-spacerun:yes'>           </span>'f.1'<span style='mso-spacerun:yes'>                  </span>[<span style='mso-spacerun:yes'>                </span>1]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'<span
+class=SpellE><span class=GramE>nan</span></span>'<span style='mso-spacerun:yes'>         </span>'-1 2'<span style='mso-spacerun:yes'>          </span>'f -+1.4'<span style='mso-spacerun:yes'>              </span>[<span style='mso-spacerun:yes'>              </span>1.4]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'<span
+class=GramE>a</span> string'<span style='mso-spacerun:yes'>    </span>'-<span
+class=SpellE>inf</span>'<span style='mso-spacerun:yes'>          </span>'f.2'<span style='mso-spacerun:yes'>                  </span>[<span style='mso-spacerun:yes'>                </span>2]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span class=GramE>'f.3'<span style='mso-spacerun:yes'>         </span>'.'</span><span style='mso-spacerun:yes'>             </span>'f.3'<span style='mso-spacerun:yes'>                  </span>[<span style='mso-spacerun:yes'>                </span>3]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'+ <span
+class=GramE>.1d-2</span>'<span style='mso-spacerun:yes'>     </span>'...'<span style='mso-spacerun:yes'>           </span>'f.10'<span style='mso-spacerun:yes'>   </span><span style='mso-spacerun:yes'>              </span>[<span style='mso-spacerun:yes'>               </span>10]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'a. .b'<span style='mso-spacerun:yes'>       </span>'.1'<span style='mso-spacerun:yes'>            </span>'f.11'<span style='mso-spacerun:yes'>                 </span>[<span style='mso-spacerun:yes'>     </span><span style='mso-spacerun:yes'>          </span>11]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'s.3TT.4'<span style='mso-spacerun:yes'>     </span>'.b a.'<span style='mso-spacerun:yes'>     </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>   </span>'+<span
+class=SpellE>inf</span>'<span style='mso-spacerun:yes'>                 </span>[<span style='mso-spacerun:yes'>              </span><span
+class=SpellE><span class=GramE>Inf</span></span>]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span>'+<span
+class=SpellE>inf</span>'<span style='mso-spacerun:yes'>        </span>'Z12e12ez'<span style='mso-spacerun:yes'>      </span>' -<span
+class=SpellE>nan</span>'<span style='mso-spacerun:yes'>                </span>[<span style='mso-spacerun:yes'>          </span><span style='mso-spacerun:yes'>    </span></span></i><st1:place><span
+ class=SpellE><i><span style='color:gray'>NaN</span></i></span></st1:place><i><span
+style='color:gray'>]<o:p></o:p></span></i></pre><pre><i><span style='color:
+gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>nan</span></span> <span class=SpellE>nan</span>'<span style='mso-spacerun:yes'>    </span>'a string'<span style='mso-spacerun:yes'>      </span>'+ <span
+class=SpellE>nan</span>'<span style='mso-spacerun:yes'>                </span>[<span style='mso-spacerun:yes'>              </span></span></i><st1:place><span
+ class=SpellE><i><span style='color:gray'>NaN</span></i></span></st1:place><i><span
+style='color:gray'>]<o:p></o:p></span></i></pre><pre><i><span style='color:
+gray'><span style='mso-spacerun:yes'>    </span>'<span class=GramE>f-1.4</span>'<span style='mso-spacerun:yes'>       </span>'a. .<span
+class=GramE>b</span>'<span style='mso-spacerun:yes'>    </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>    </span>'<span
+class=SpellE>nan</span>'<span style='mso-spacerun:yes'>                  </span>[<span style='mso-spacerun:yes'>              </span></span></i><st1:place><span
+ class=SpellE><i><span style='color:gray'>NaN</span></i></span></st1:place><i><span
+style='color:gray'>]<o:p></o:p></span></i></pre><pre><i><span style='color:
+gray'><span style='mso-spacerun:yes'>    </span>'x-3.2e4y'<span style='mso-spacerun:yes'>    </span>'f -+1.4'<span style='mso-spacerun:yes'>     </span><span style='mso-spacerun:yes'>  </span>'--- ASCII NUMBERS'<span style='mso-spacerun:yes'>    </span>'--- ASCII NUMBERS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'<span
+class=SpellE><span class=GramE>inf</span></span> -<span class=SpellE>inf</span>'<span style='mso-spacerun:yes'>  </span><span style='mso-spacerun:yes'>  </span>'f-1.4'<span style='mso-spacerun:yes'>         </span>' <span
+class=SpellE>nan</span> <span class=SpellE>nan</span>'<span style='mso-spacerun:yes'>             </span>' <span
+class=SpellE>nan</span> <span class=SpellE>nan</span>'<span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'+ <span
+class=SpellE><span class=GramE>nan</span></span>'<span style='mso-spacerun:yes'>       </span>'f.1'<span style='mso-spacerun:yes'>           </span>'+ .1e-.2'<span style='mso-spacerun:yes'>             </span>'+ .1e-.2'<span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f.2'<span style='mso-spacerun:yes'>         </span>'f.10'<span style='mso-spacerun:yes'>          </span>'-1 2'<span style='mso-spacerun:yes'>                 </span>'-1 2'<span style='mso-spacerun:yes'>             </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f.11'<span style='mso-spacerun:yes'>  </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'f.11'</span><span style='mso-spacerun:yes'>          </span>'Z12e12ez'<span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'Z12e12ez'</span><span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'Z12e12ez'<span style='mso-spacerun:yes'>    </span>'f.2'<span style='mso-spacerun:yes'>      </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>    </span>'<span
+class=SpellE>inf</span> -<span class=SpellE>inf</span>'<span style='mso-spacerun:yes'>             </span>'<span
+class=SpellE>inf</span> -<span class=SpellE>inf</span>'<span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'z12e12ez'<span style='mso-spacerun:yes'>    </span>'f.3'<span style='mso-spacerun:yes'>           </span>'s.3TT.4'<span style='mso-spacerun:yes'>              </span><span
+class=SpellE>'s.3TT.4'</span><span style='mso-spacerun:yes'>          </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f -+1.4'<span style='mso-spacerun:yes'>     </span>'<span
+class=SpellE>inf</span> -<span class=SpellE>inf</span>'<span style='mso-spacerun:yes'>      </span>'z12e12ez'<span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'z12e12ez'</span><span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>' . .. '<span style='mso-spacerun:yes'>      </span>'<span
+class=SpellE><span class=GramE>nan</span></span>'<span style='mso-spacerun:yes'>           </span>'--- ASCII STRINGS'<span style='mso-spacerun:yes'>    </span>'--- ASCII STRINGS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f.10'<span style='mso-spacerun:yes'>        </span>'s.3TT.4'<span style='mso-spacerun:yes'>       </span><span
+class=GramE>' .</span> .. '<span style='mso-spacerun:yes'>         </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'</span> . .. '<span style='mso-spacerun:yes'>           </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'.'<span style='mso-spacerun:yes'>           </span><span
+class=GramE>'x-3.2e4y'<span style='mso-spacerun:yes'>      </span>'.'</span><span style='mso-spacerun:yes'>                    </span><span
+class=SpellE>'.'</span><span style='mso-spacerun:yes'>                </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'-.1'<span style='mso-spacerun:yes'>     </span><span style='mso-spacerun:yes'>    </span>'z12e12ez'<span style='mso-spacerun:yes'>      </span>'...'<span style='mso-spacerun:yes'>                  </span><span
+class=SpellE>'</span>...'<span style='mso-spacerun:yes'>              </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>           </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span>'.b a.'<span style='mso-spacerun:yes'>                </span>'.b a.'<span style='mso-spacerun:yes'>            </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>   </span><span
+class=GramE>' <span class=SpellE>'</span></span><span style='mso-spacerun:yes'>           </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span>'a string'<span style='mso-spacerun:yes'>             </span>'a string'<span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>   </span><span
+class=GramE>' <span class=SpellE>'</span></span><span style='mso-spacerun:yes'>           </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span>'a. .b'<span style='mso-spacerun:yes'>                </span>'a. .<span
+class=GramE>b</span>'<span style='mso-spacerun:yes'>            </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre style='margin-left:
+22.5pt'><span class=comment>% - show results</span></pre><pre style='margin-left:
+22.5pt'><span style='mso-tab-count:2'>          </span><span class=GramE>o</span></pre><pre><i><span
+style='color:gray'>o = <o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>          </span><span
+class=GramE>magic</span>: 'ASORT'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>      </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>     </span><span
+class=SpellE><span class=GramE>ver</span></span>: '</span></i><st1:date
+Year="2005" Day="30" Month="3"><i><span style='color:gray'>30-Mar-2005</span></i></st1:date><i><span
+style='color:gray'> </span></i><st1:time Minute="57" Hour="11"><i><span
+ style='color:gray'>11:57:07</span></i></st1:time><i><span style='color:gray'>'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>           </span>time: '30-Mar-2005 11:57:17'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>        </span><span
+class=GramE>runtime</span>: 0.047<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span
+class=SpellE>input_class</span>: 'cell'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span
+class=SpellE>input_msize</span>: [29 1]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span
+class=SpellE>input_bytes</span>: 2038<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span
+class=SpellE>strng_class</span>: 'char'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span
+class=SpellE>strng_msize</span>: [29 8]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span
+class=SpellE>strng_bytes</span>: 464<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>            </span><span
+class=SpellE><span class=GramE>anr</span></span>: {16x1 cell}<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>      </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>     </span><span
+class=SpellE><span class=GramE>snr</span></span>: {7x1 cell}<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>      </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>     </span><span
+class=SpellE><span class=GramE>str</span></span>: {6x1 cell}<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>              </span><span
+class=GramE>c</span>: [29x12 char]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>              </span><span
+class=GramE>t</span>: [29x12 logical]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>              </span><span
+class=GramE>n</span>: [16x12 char]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>  </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>           </span><span
+class=GramE>d</span>: [16x1 double]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre style='margin-left:
+22.5pt'><span style='mso-tab-count:2'>          </span><span class=SpellE>o.anr</span></pre><pre><span
+class=SpellE><span class=GramE><i><span style='color:gray'>ans</span></i></span></span><i><span
+style='color:gray'> = <o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>   </span>'-<span
+class=SpellE><span class=GramE>inf</span></span>'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'<span
+class=GramE>x-3.2e4y</span>'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'<span
+class=GramE>f-1.4</span>'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'-.1'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'+ <span
+class=GramE>.1d-2</span>'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'.1'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f.1'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f -+1.4'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f.2'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f.3'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f.10'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'f.11'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span>'+<span
+class=SpellE>inf</span>'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span class=GramE>' -</span><span
+class=SpellE>nan</span>'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>  </span>'+ <span
+class=SpellE><span class=GramE>nan</span></span>'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'<span
+class=SpellE><span class=GramE>nan</span></span>'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre style='margin-left:
+22.5pt'><span class=comment>% - run <b style='mso-bidi-font-weight:normal'>ASORT</b> with <b
+style='mso-bidi-font-weight:normal'>no-space</b>/<b style='mso-bidi-font-weight:
+normal'>template</b> options</span></pre><pre style='margin-left:22.5pt'><span
+class=comment>%<span style='mso-spacerun:yes'>   </span><span class=GramE>NOTE</span> the impact of -w/-t order!</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:2'>          </span>s<span
+class=GramE>={</span><span class=string>'ff - 1'</span>,<span class=string>'ff + 1'</span>,<span
+class=string>'- 12'</span>};</pre><pre><i><span style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre
+style='margin-left:22.5pt'><span class=comment>%<span style='mso-spacerun:yes'>   </span>RAW</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:2'>          </span>o=<span
+class=SpellE>asort</span>(s,<span class=string>'-v'</span>);</pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'INPUT'<span style='mso-spacerun:yes'>     </span>'ASCII SORT'<span style='mso-spacerun:yes'>    </span>'NUM SORT'<span style='mso-spacerun:yes'>             </span>'NUM READ'<span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'<span
+class=GramE>ff</span> - 1'<span style='mso-spacerun:yes'>    </span>'- 12'<span style='mso-spacerun:yes'>          </span>'--- NUMERICAL'<span style='mso-spacerun:yes'>        </span>'--- NUMBERS'<span style='mso-spacerun:yes'>      </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'<span
+class=GramE>ff</span> + 1'<span style='mso-spacerun:yes'>    </span>'ff + 1'<span style='mso-spacerun:yes'>        </span>'ff + 1'<span style='mso-spacerun:yes'>               </span>[<span style='mso-spacerun:yes'>                </span>1]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'- 12'<span style='mso-spacerun:yes'>      </span>'ff - 1'<span style='mso-spacerun:yes'>        </span>'ff - 1'<span style='mso-spacerun:yes'>               </span>[<span style='mso-spacerun:yes'>                </span>1]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>         </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'</span>- 12'<span style='mso-spacerun:yes'>                 </span>[<span style='mso-spacerun:yes'>               </span>12]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>         </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>    </span><span style='mso-spacerun:yes'>   </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'</span>--- ASCII NUMBERS'<span style='mso-spacerun:yes'>    </span>'--- ASCII NUMBERS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>         </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'</span>--- ASCII STRINGS'<span style='mso-spacerun:yes'>    </span>'--- ASCII STRINGS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre style='margin-left:
+22.5pt'><span class=comment>%<span style='mso-spacerun:yes'>   </span><span
+class=GramE>remove</span> <span class=SpellE><b style='mso-bidi-font-weight:
+normal'>SPACE</b>s</span></span></pre><pre style='margin-left:22.5pt'><span
+style='mso-tab-count:2'>          </span>o=<span class=SpellE>asort</span>(s,<span
+class=string>'-v'</span>,<span class=string>'-w'</span>);</pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'INPUT'<span style='mso-spacerun:yes'>    </span>'ASCII SORT'<span style='mso-spacerun:yes'>    </span>'NUM SORT'<span style='mso-spacerun:yes'>             </span>'NUM READ'<span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'ff-1' <span style='mso-spacerun:yes'>    </span>'-12'<span style='mso-spacerun:yes'>           </span>'--- NUMERICAL'<span style='mso-spacerun:yes'>        </span>'--- NUMBERS'<span style='mso-spacerun:yes'>      </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'<span
+class=GramE>ff+</span>1'<span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'ff+1'</span><span style='mso-spacerun:yes'>          </span>'-12'<span style='mso-spacerun:yes'>                  </span>[<span style='mso-spacerun:yes'>              </span>-12]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'-12'<span style='mso-spacerun:yes'>      </span>'ff-1'<span style='mso-spacerun:yes'>    </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'ff-1'</span><span style='mso-spacerun:yes'>                 </span>[<span style='mso-spacerun:yes'>               </span>-1]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>        </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span>'ff+1'<span style='mso-spacerun:yes'>        </span><span style='mso-spacerun:yes'>         </span>[<span style='mso-spacerun:yes'>                </span>1]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>        </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'</span>--- ASCII NUMBERS'<span style='mso-spacerun:yes'>    </span>'--- ASCII NUMBERS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>        </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'</span>--- ASCII STRINGS'<span style='mso-spacerun:yes'>    </span>'--- ASCII STRINGS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre style='margin-left:
+22.5pt'><span class=comment>%<span style='mso-spacerun:yes'>   </span><span
+class=GramE>remove</span> <b style='mso-bidi-font-weight:normal'>TEMPLATE</b>(s)</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:2'>          </span>o=<span
+class=SpellE>asort</span>(s,<span class=string>'-v'</span>,<span class=string>'-t'</span><span
+class=GramE>,{</span><span class=string>'ff'</span>,<span class=string>'1'</span>});</pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'INPUT'<span style='mso-spacerun:yes'>    </span>'ASCII SORT'<span style='mso-spacerun:yes'>    </span>'NUM SORT'<span style='mso-spacerun:yes'>             </span>'NUM READ'<span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span class=GramE>' -</span> ' <span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'</span> + '<span style='mso-spacerun:yes'>           </span><span
+class=SpellE>'</span>--- NUMERICAL'<span style='mso-spacerun:yes'>        </span>'--- NUMBERS'<span style='mso-spacerun:yes'>      </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span class=GramE>' +</span> ' <span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'</span> - '<span style='mso-spacerun:yes'>           </span><span
+class=SpellE>'</span>- 2'<span style='mso-spacerun:yes'>                  </span>[<span style='mso-spacerun:yes'>                </span>2]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'- 2'<span style='mso-spacerun:yes'>      </span>'- 2'<span style='mso-spacerun:yes'>           </span>'--- ASCII NUMBERS'<span style='mso-spacerun:yes'>   </span><span style='mso-spacerun:yes'> </span>'--- ASCII NUMBERS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>        </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'</span>--- ASCII STRINGS'<span style='mso-spacerun:yes'>    </span>'--- ASCII STRINGS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span>' <span
+class=SpellE>'</span><span style='mso-spacerun:yes'>        </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'</span> + '<span style='mso-spacerun:yes'>                  </span><span
+class=SpellE>'</span> + '<span style='mso-spacerun:yes'>              </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>   </span>' <span
+class=SpellE>'</span><span style='mso-spacerun:yes'>        </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'</span> - '<span style='mso-spacerun:yes'>                  </span><span
+class=SpellE>'</span> - '<span style='mso-spacerun:yes'>              </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre style='margin-left:
+22.5pt'><span class=comment>%<span style='mso-spacerun:yes'>   </span><span
+class=GramE>remove</span> <b style='mso-bidi-font-weight:normal'>TEMPLATE</b>(s) than <span
+class=SpellE><b style='mso-bidi-font-weight:normal'>SPACE</b>s</span></span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:2'>          </span>o=<span
+class=SpellE>asort</span>(s,<span class=string>'-v'</span>,<span class=string>'-t'</span>,<span
+class=string>'1'</span>,<span class=string>'-w'</span>);</pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'INPUT'<span style='mso-spacerun:yes'>    </span>'ASCII SORT'<span style='mso-spacerun:yes'>    </span>'NUM SORT'<span style='mso-spacerun:yes'>             </span>'NUM READ'<span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'ff-'<span style='mso-spacerun:yes'>      </span>'-2'<span style='mso-spacerun:yes'>            </span>'--- NUMERICAL'<span style='mso-spacerun:yes'>        </span>'--- NUMBERS'<span style='mso-spacerun:yes'>      </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'ff+' <span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'ff+'</span><span style='mso-spacerun:yes'>           </span>'-2'<span style='mso-spacerun:yes'>                </span><span style='mso-spacerun:yes'>   </span>[<span style='mso-spacerun:yes'>               </span>-2]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'-2'<span style='mso-spacerun:yes'>       </span>'ff-'<span style='mso-spacerun:yes'>           </span>'--- ASCII NUMBERS'<span style='mso-spacerun:yes'>    </span>'--- ASCII NUMBERS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>        </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'</span>--- ASCII STRINGS'<span style='mso-spacerun:yes'>    </span>'--- ASCII STRINGS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>        </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span>'ff+'<span style='mso-spacerun:yes'>                  </span><span
+class=SpellE>'ff+'</span><span style='mso-spacerun:yes'>              </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>    </span><span style='mso-spacerun:yes'>    </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span>'ff-'<span style='mso-spacerun:yes'>                  </span><span
+class=SpellE>'ff-'</span><span style='mso-spacerun:yes'>              </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre style='margin-left:
+22.5pt'><span class=comment>%<span style='mso-spacerun:yes'>   </span><span
+class=GramE>remove</span> <span class=SpellE><b style='mso-bidi-font-weight:
+normal'>SPACE</b>s</span> than <b style='mso-bidi-font-weight:normal'>TEMPLATE</b>(s)</span></pre><pre
+style='margin-left:22.5pt'><span style='mso-tab-count:2'>          </span>o=<span
+class=SpellE>asort</span>(s,<span class=string>'-v'</span>,<span class=string>'-w'</span>,<span
+class=string>'-t'</span>,<span class=string>'1'</span>);</pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'INPUT'<span style='mso-spacerun:yes'>    </span>'ASCII SORT'<span style='mso-spacerun:yes'>    </span>'NUM SORT'<span style='mso-spacerun:yes'>             </span>'NUM READ'<span style='mso-spacerun:yes'>         </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'ff- '<span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'</span>- 2'<span style='mso-spacerun:yes'>           </span>'--- NUMERICAL'<span style='mso-spacerun:yes'>   </span><span style='mso-spacerun:yes'>     </span>'--- NUMBERS'<span style='mso-spacerun:yes'>      </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'ff+ '<span style='mso-spacerun:yes'>     </span>'ff+ '<span style='mso-spacerun:yes'>    </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'</span>- 2'<span style='mso-spacerun:yes'>                  </span>[<span style='mso-spacerun:yes'>                </span>2]<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'>    </span>'- 2'<span style='mso-spacerun:yes'>      </span>'ff- '<span style='mso-spacerun:yes'>    </span><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>     </span><span
+class=SpellE>'</span>--- ASCII NUMBERS'<span style='mso-spacerun:yes'>    </span>'--- ASCII NUMBERS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>        </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span><span
+class=SpellE>'</span>--- ASCII STRINGS'<span style='mso-spacerun:yes'>    </span>'--- ASCII STRINGS'<o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'> <span style='mso-spacerun:yes'>   </span><span class=GramE>' <span
+class=SpellE>'</span></span><span style='mso-spacerun:yes'>  </span><span style='mso-spacerun:yes'>      </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span>'ff+ '<span style='mso-spacerun:yes'>                 </span>'ff+ '<span style='mso-spacerun:yes'>             </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><span style='mso-spacerun:yes'> </span><span style='mso-spacerun:yes'>   </span><span
+class=GramE>' <span class=SpellE>'</span></span><span style='mso-spacerun:yes'>        </span><span
+class=SpellE>'</span> <span class=SpellE>'</span><span style='mso-spacerun:yes'>             </span>'ff- '<span style='mso-spacerun:yes'>                 </span>'ff- '<span style='mso-spacerun:yes'>             </span><o:p></o:p></span></i></pre><pre><i><span
+style='color:gray'><o:p>&nbsp;</o:p></span></i></pre>
+
+<p class=footer style='tab-stops:45.8pt 91.6pt 137.4pt 183.2pt 229.0pt 274.8pt 320.6pt 366.4pt 412.2pt 458.0pt 503.8pt 549.6pt 595.4pt 641.2pt 687.0pt 732.8pt'><br>
+Published with MATLAB® 7.0.4<o:p></o:p></p>
+
+</div>
+
+<!--
+##### SOURCE BEGIN #####
+% ASORT
+% a pedestrian NUMERICAL SORTER of ALPHANUMERIC data
+
+% - create some data
+		d = {
+%	strings with one valid alphanumeric number
+%	sorted numerically
+			'-inf'
+			'x-3.2e4y'
+			'f-1.4'
+			'-.1'
+			'+ .1d-2'
+			'.1'
+			'f.1'
+			'f -+1.4'
+			'f.2'
+			'f.3'
+			'f.10'
+			'f.11'
+			'+inf'
+			' -nan'
+			'+ nan'
+			'nan'
+%	strings with many numbers or invalid/ambiguous numbers
+%	sorted in ascii dictionary order
+			' nan nan'
+			'+ .1e-.2'
+			'-1 2'
+			'Z12e12ez'
+			'inf -inf'
+			's.3TT.4'
+			'z12e12ez'
+%	strings without numbers
+%	sorted in ascii dictionary order
+			' . .. '
+			'.'
+			'...'
+			'.b a.'
+			'a string'
+			'a. .b'
+		};
+%   ... and scramble it...
+		rand('seed',10);
+		d=d(randperm(numel(d)));
+
+% - run ASORT with verbose output
+%   and keep additional results
+		o=asort(d,'-v','-d');
+% - or
+%		p=asort(char(d));
+
+% - show results
+		o
+		o.anr
+
+% - run ASORT with no-space/template options
+%   NOTE the impact of -t/-w order!
+		s={'ff - 1','ff + 1','- 12'};
+%   RAW
+		o=asort(s,'-v');
+%   remove SPACEs
+		o=asort(s,'-v','-w');
+%   remove TEMPLATE(s)
+		o=asort(s,'-v','-t',{'ff','1'});
+%   remove TEMPLATE(s) than SPACEs
+		o=asort(s,'-v','-t','1','-w');
+%   remove SPACEs than TEMPLATE(s)
+		o=asort(s,'-v','-w','-t','1');
+
+
+##### SOURCE END #####
+-->
+</body>
+
+</html>
diff --git a/sourcecodes/bnt-master/KPMtools/asdemo.m b/sourcecodes/bnt-master/KPMtools/asdemo.m
new file mode 100644
index 00000000..6de98ad9
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/asdemo.m
@@ -0,0 +1,70 @@
+% ASORT
+% a pedestrian NUMERICAL SORTER of ALPHANUMERIC data
+
+% - create some data
+		d = {
+%		strings with one valid alphanumeric number
+%		sorted numerically
+			'-inf'
+			'x-3.2e4y'
+			'f-1.4'
+			'-.1'
+			'+ .1d-2'
+			'.1'
+			'f.1'
+			'f -+1.4'
+			'f.2'
+			'f.3'
+			'f.10'
+			'f.11'
+			'+inf'
+			' -nan'
+			'+ nan'
+			'nan'
+%		strings with many numbers or invalid/ambiguous numbers
+%		sorted in ascii dictionary order
+			' nan nan'
+			'+ .1e-.2'
+			'-1 2'
+			'Z12e12ez'
+			'inf -inf'
+			's.3TT.4'
+			'z12e12ez'
+%		strings without numbers
+%		sorted in ascii dictionary order
+			' . .. '
+			'.'
+			'...'
+			'.b a.'
+			'a string'
+			'a. .b'
+		};
+%   ... and scramble it...
+		rand('seed',10);
+		d=d(randperm(numel(d)));
+
+% - run ASORT with
+%   verbose output:		<-v>
+%   keep additional results:	<-d>
+		o=asort(d,'-v','-d');
+% - or
+%		p=asort(char(d),'-v','-d');
+
+% - show results
+		o
+		o.anr
+
+% - run ASORT with no-space/template options
+%   NOTE the impact of -w/-t order!
+		s={'ff - 1','ff + 1','- 12'};
+%   RAW
+		o=asort(s,'-v');
+%   remove SPACEs
+		o=asort(s,'-v','-w');
+%   remove TEMPLATE(s)
+		o=asort(s,'-v','-t',{'ff','1'});
+%   remove TEMPLATE(s) than SPACEs
+		o=asort(s,'-v','-t','1','-w');
+%   remove SPACEs than TEMPLATE(s)
+		o=asort(s,'-v','-w','-t','1');
+
diff --git a/sourcecodes/bnt-master/KPMtools/asort.m b/sourcecodes/bnt-master/KPMtools/asort.m
new file mode 100644
index 00000000..df6be4b3
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/asort.m
@@ -0,0 +1,376 @@
+%[ANR,SNR,STR]	=  ASORT(INP,'OPT',...);
+% S		=  ASORT(INP,'OPT',...);
+%		   to sort alphanumeric strings numerically if
+%		   they contain one properly formatted number
+%		   otherwise, ascii dictionary sorting is applied
+%
+% INP	unsorted input:
+%	- a char array
+%	- a cell array of strings
+% OPT	options
+%  -s	- sorting option
+%	  '-s','ascend'					[def]
+%	  '-s','descend'
+%  -st	- force output form S				[def: nargout dependent]
+%  -t	- replace matching template(s) with one space
+%	  prior to sorting
+%	  '-t','template'
+%	  '-t',{'template1','template2',...}
+%  -w	- remove space(s) prior to sorting
+%
+%	  NOTE	-t/-w options are processed in the
+%		      order that they appear in
+%		      the command line
+%
+%  -v	- verbose output				[def: quiet]
+%  -d	- debug mode
+%	  save additional output in S
+%	  .c:	lex parser input
+%	  .t:	lex parser table
+%	  .n:	lex parser output
+%	  .d:	numbers read from .n
+%
+% ANR	numerically sorted alphanumeric strings		[eg, 'f.-1.5e+2x.x']
+%	- contain one number that can be read by
+%	  <strread> | <sscanf>
+% SNR	ascii dict  sorted alphanumeric strings
+% http://www.mathworks.com/matlabcentral/fileexchange/loadFile.do?objectId=7212#
+%
+%	- contain more than one number			[eg, 'f.-1.5e +2.x']
+%	- contain incomplete|ambiguous numbers		[eg, 'f.-1.5e+2.x']
+% STR	ascii dict  sorted strings
+%	- contain no numbers				[eg, 'a test']
+%
+% S	structure with fields
+%	.anr
+%	.srn
+%	.str
+
+% created:
+%	us	03-Mar-2002
+% modified:
+%	us	30-Mar-2005 11:57:07 	/ TMW R14.sp2
+
+%--------------------------------------------------------------------------------
+function	varargout=asort(inp,varargin)
+
+varargout(1:nargout)={[]};
+if	~nargin
+	help(mfilename);
+	return;
+end
+
+% - common parameters/options
+n=[];
+ds=[];
+anr={};
+snr={};
+str={};
+smod='ascend';	% sorting option
+tmpl={};	% template(s)
+sflg=false;	% output  mode: structure
+tflg=false;	% remove  template(s)
+dflg=false;	% debug   mode
+vflg=false;	% verbose output
+wflg=false;	% remove  spaces
+
+if	nargin > 1
+	ix=find(strcmp('-s',varargin));
+	if	~isempty(ix) && nargin > ix(end)+1
+		smod=varargin{ix(end)+1};
+	end
+	ix=find(strcmp('-t',varargin));
+	if	~isempty(ix) && nargin > ix(end)+1
+		tflg=ix(end);
+		tmpl=varargin{ix(end)+1};
+	end
+	if	find(strcmp('-d',varargin));
+		dflg=true;
+	end
+	if	find(strcmp('-st',varargin));
+		sflg=true;
+	end
+	if	find(strcmp('-v',varargin));
+		vflg=true;
+	end
+	ix=find(strcmp('-w',varargin));
+	if	~isempty(ix)
+		wflg=ix(end);
+	end
+end
+%   spec numbers
+ntmpl={
+	' inf '
+	'+inf '
+	'-inf '
+	' nan '
+	'+nan '
+	'-nan '
+	};
+%   spec chars
+ctmpl={
+	'.'	% decimal point
+	'd'	% exponent
+	'e'	% exponent
+	};
+
+if	nargout <= 3
+	varargout{1}=inp;
+else
+	disp(sprintf('ASORT> too many output args [%-1d/%-1d]\n',nargout,3));
+	help(mfilename);
+	return;
+end
+if	isempty(inp)
+	disp(sprintf('ASORT> input is empty'));
+	return;
+end
+
+ti=clock;
+winp=whos('inp');
+switch	winp.class
+	case	'cell'
+		if	~iscellstr(inp)
+			disp(sprintf('ASORT> cell is not an array of strings'));
+			return;
+		end
+		inp=inp(:);
+		[ins,inx]=sort(inp);
+	case	'char'
+		%		[ins,inx]=sortrows(inp);
+		inp=cstr(inp);
+	otherwise
+		disp(sprintf('ASORT> does not sort input of class <%s>',winp.class));
+		return;
+end
+
+inp=inp(:);
+inp=setinp(inp,tmpl,[tflg wflg]);
+[ins,inx]=sort(inp);
+if	strcmp(smod,'descend')
+	ins=ins(end:-1:1,:);
+	inx=inx(end:-1:1);
+end
+ins=inp(inx);
+c=lower(char(ins));
+wins=whos('c');
+[cr,cc]=size(c);
+
+% - LEXICAL PARSER
+%--------------------------------------------------------------------------------
+% - extend input on either side for search
+c=[' '*ones(cr,2) c ' '*ones(cr,2)];
+
+% - search for valid alphanumeric items in strings
+%   numbers/signs
+t=(c>='0'&c<='9');
+t=t|c=='-';
+t=t|c=='+';
+[tr,tc]=size(t);
+%   decimal points
+%   note: valid numbers with dec points must follow these templates
+%         nr.nr
+%	  sign.nr
+%         nr.<SPACE>
+%         <SPACE>.nr
+ix1=	 t(:,1:end-2) & ...
+	~isletter(c(:,1:end-2)) & ...
+	c(:,2:end-1)=='.';
+t(:,2:end-1)=t(:,2:end-1)|ix1;
+ix1=	(t(:,3:end) & ...
+	(~isletter(c(:,3:end)) & ...
+	~isletter(c(:,1:end-2))) | ...
+	(c(:,3:end)=='e' | ...
+	c(:,3:end)=='d')) & ...
+	c(:,2:end-1)=='.';
+t(:,2:end-1)=t(:,2:end-1)|ix1;
+%		t(:,3:end)=t(:,3:end)|ix1;
+%   signs
+t(c=='-')=false;
+t(c=='+')=false;
+ix1=	 t(:,3:end) & ...
+	(c(:,2:end-1)=='-' | ...
+	c(:,2:end-1)=='+');
+t(:,2:end-1)=t(:,2:end-1)|ix1;
+%   exponents
+ix1=	 t(:,1:end-2) & ...
+	(c(:,2:end-1)=='e' | ...
+	c(:,2:end-1)=='d');
+t(:,2:end-1)=t(:,2:end-1)|ix1;
+%   spec numbers
+c=reshape(c.',1,[]);
+t=t';
+ic=[];
+for	j=1:numel(ntmpl)
+	ic=[ic,strfind(c,ntmpl{j})];
+end
+ic=sort(ic);
+for	i=1:numel(ic)
+	ix=ic(i)+0:ic(i)+4;
+	t(ix)=true;
+end
+t=t';
+c=reshape(c.',[tc,tr]).';
+t(c==' ')=false;
+%--------------------------------------------------------------------------------
+
+% - only allow one number per string
+il=~any(t,2);
+ib=strfind(reshape(t.',1,[]),[0 1]);
+if	~isempty(ib)
+	ixe=cell(3,1);
+	n=reshape(char(t.*c).',1,[]);
+	for	i=1:numel(ctmpl)
+		id=strfind(n,ctmpl{i});
+		if	~isempty(id)
+			[dum,dum,ixu{i},ixe{i}]=dupinx(id,tc);
+		end
+	end
+	in=false(tr,1);
+	im=in;
+	%   must check for anomalous cases like <'.d'>
+	id=sort(...
+		[find(n>='0' & n<='9'),...
+		strfind(n,'inf'),...
+		strfind(n,'nan')]);
+	%		[ibu,ibd,ixbu,ixe{i+1}]=dupinx(id,tc);
+	[ibu,ibd,ixbu,ixbd]=dupinx(id,tc);
+	in(ixbu)=true;
+	in(ixbd)=true;
+	[ibu,ibd,ixbu,ixbd]=dupinx(ib,tc);
+	im(ixbu)=true;
+	in=in&im;
+	in([ixe{:}])=false;
+	il=~any(t,2);
+	ia=~(in|il);
+
+	% - read valid strings
+	n=t(in,:).*c(in,:);
+	n(n==0)=' ';
+	n=char(n);
+	dn=strread(n.','%n');
+	if	numel(dn) ~= numel(find(in))
+		%disp(sprintf('ASORT> unexpected fatal error reading input!'));
+		if	nargout
+			s.c=c;
+			s.t=t;
+			s.n=n;
+			s.d=dn;
+			varargout{1}=s;
+		end
+		return;
+	end
+
+	% - sort numbers
+	[ds,dx]=sort(dn,1,smod);
+	in=find(in);
+	anr=ins(in(dx));
+	snr=ins(ia);
+end
+str=ins(il);
+to=clock;
+
+% - prepare output
+if	nargout < 3 || sflg
+	s.magic='ASORT';
+	s.ver='30-Mar-2005 11:57:07';
+	s.time=datestr(clock);
+	s.runtime=etime(to,ti);
+	s.input_class=winp.class;
+	s.input_msize=winp.size;
+	s.input_bytes=winp.bytes;
+	s.strng_class=wins.class;
+	s.strng_msize=wins.size;
+	s.strng_bytes=wins.bytes;
+	s.anr=anr;
+	s.snr=snr;
+	s.str=str;
+	if	dflg
+		s.c=c;
+		s.t=t;
+		s.n=n;
+		s.d=ds;
+	end
+	varargout{1}=s;
+else
+	s={anr,snr,str};
+	for	i=1:nargout
+		varargout{i}=s{i};
+	end
+end
+
+if	vflg
+	inp=cstr(inp);
+	an=[{'--- NUMERICAL'};		anr];
+	as=[{'--- ASCII NUMBERS'};	snr];
+	at=[{'--- ASCII STRINGS'};	str];
+	nn=[{'--- NUMBERS'};		num2cell(ds)];
+	ag={' ';' ';' '};
+	u=[{'INPUT'};			inp;ag];
+	v=[{'ASCII SORT'};		ins;ag];
+	w=[{'NUM SORT'};		an;as;at];
+	x=[{'NUM READ'};		nn;as;at];
+	w=[u,v,w,x];
+	disp(w);
+end
+
+return;
+%--------------------------------------------------------------------------------
+function	c=cstr(s)
+% - bottleneck waiting for a good <cellstr> replacement
+%   it consumes ~75% of <asort>'s processing time!
+
+c=s;
+if	ischar(s)
+	sr=size(s,1);
+	c=cell(sr,1);
+	for	i=1:sr
+		c{i}=s(i,:);	% no deblanking!
+	end
+end
+return;
+%--------------------------------------------------------------------------------
+function	[idu,idd,ixu,ixd]=dupinx(ix,nc)
+% - check for more than one entry/row in a matrix of column size <nc>
+%   unique    indices:	idu / ixu
+%   duplicate indices:	idd / ixd
+
+if	isempty(ix)
+	idu=[];
+	idd=[];
+	ixu=[];
+	ixd=[];
+	return;
+end
+id=fix(ix/nc)+1;
+idi=diff(id)~=0;
+ide=[true idi];
+idb=[idi true];
+idu=idb & ide;
+idd=idb==1 & ide==0;
+ixu=id(idu);
+ixd=id(idd);
+return;
+%--------------------------------------------------------------------------------
+function	inp=setinp(inp,tmpl,flg)
+% - remove space(s) and/or templates
+
+if	isempty(inp) || ~any(flg)
+	return;
+end
+
+for	i=sort(flg)
+	switch	i
+		case	flg(1)
+			if	ischar(tmpl)
+				tmpl={tmpl};
+			end
+			for	i=1:numel(tmpl)
+				inp=strrep(inp,tmpl{i},' ');
+			end
+		case	flg(2)
+			inp=strrep(inp,' ','');
+	end
+end
+return;
+%--------------------------------------------------------------------------------
diff --git a/sourcecodes/bnt-master/KPMtools/assertBNT.m b/sourcecodes/bnt-master/KPMtools/assertBNT.m
new file mode 100644
index 00000000..2d0cf960
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/assertBNT.m
@@ -0,0 +1,10 @@
+function assertBNT(pred, str)
+% ASSERT Raise an error if the predicate is not true.
+% assert(pred, string)
+
+if nargin<2, str = ''; end
+
+if ~pred
+  s = sprintf('assertion violated: %s', str);
+  error(s);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/assignEdgeNums.m b/sourcecodes/bnt-master/KPMtools/assignEdgeNums.m
new file mode 100644
index 00000000..5d9a2a0d
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/assignEdgeNums.m
@@ -0,0 +1,32 @@
+function [edge_id, nedges] = assignEdgeNums(adj_mat)
+% give each edge a unique number
+% we number (i,j) for j>i first, in row, column order.
+% Then we number the reverse links
+
+nnodes = length(adj_mat);
+edge_id = zeros(nnodes);
+e = 1;
+for i=1:nnodes
+  for j=i+1:nnodes
+    if adj_mat(i,j)
+      edge_id(i,j) = e;
+      e = e+1;
+    end
+  end
+end
+
+nedges = e-1;
+tmp = edge_id;
+ndx = find(tmp);
+tmp(ndx) = tmp(ndx)+nedges;
+edge_id = edge_id + triu(tmp)';
+
+
+if 0
+ndx = find(adj_mat);
+nedges = length(ndx);
+nnodes = length(adj_mat);
+edge_id = zeros(1, nnodes*nnodes);
+edge_id(ndx) = 1:nedges; 
+edge_id = reshape(edge_id, nnodes, nnodes);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/assign_cols.m b/sourcecodes/bnt-master/KPMtools/assign_cols.m
new file mode 100644
index 00000000..84cc9199
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/assign_cols.m
@@ -0,0 +1,36 @@
+function M = assign_cols(cols, vals, M)
+% ASSIGN_COLS Assign values to columns of a matrix
+% function M = assign_cols(M, cols, vals, M)
+%
+% Example:
+% M = assign_cols(data, ones(1,N))
+% will construct a 1-of-K encoding of the data, where K=ncols=max(data) and N=nrows=length(data)
+%
+% Example:
+% M = zeros(3,2);
+% M = assign_cols([1 2 1], [10 20 30], M)
+% is equivalent to
+% M(1, 1) = 10
+% M(2, 2) = 20
+% M(3, 1) = 30
+%
+
+if nargin < 3
+  nr = length(cols);
+  nc = max(cols);
+  M = zeros(nr, nc);
+else
+  [nr nc] = size(M);
+end
+
+if 0
+for r=1:nr
+  M(r, cols(r)) = vals(r);
+end
+end
+
+if 1
+rows = 1:nr;
+ndx = subv2ind([nr nc], [rows(:) cols(:)]);
+M(ndx) = vals;
+end
diff --git a/sourcecodes/bnt-master/KPMtools/axis_pct.m b/sourcecodes/bnt-master/KPMtools/axis_pct.m
new file mode 100644
index 00000000..208481eb
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/axis_pct.m
@@ -0,0 +1,70 @@
+function ax = axis_pct(pct)
+% AXIS_PCT       Set reasonable axis limits.
+% AXIS_PCT(pct) sets axis limits to extend pct% beyond limits of plotted 
+% objects.  Default is 5%.
+% Works for linear or log scale.
+% Unfortunately, the axes won't change when new points are plotted.
+
+if nargin < 1
+  pct = 0.05;
+end
+ax = [Inf -Inf Inf -Inf Inf -Inf];
+
+% find bounding box of plotted objects
+children = get(gca,'children');
+for child = children'
+  if strcmp(get(child,'type'),'text')
+    xyz = get(child,'position');
+    % need to determine bounding box of the text
+    c([1 2]) = xyz(1);
+    c([3 4]) = xyz(2);
+    c([5 6]) = xyz(3);
+  else
+    x = get(child,'xdata');
+    c(1) = min(x);
+    c(2) = max(x);
+    y = get(child,'ydata');
+    c(3) = min(y);
+    c(4) = max(y);
+    z = get(child,'zdata');
+    if isempty(z)
+      c([5 6]) = 0;
+    else
+      c(5) = min(z);
+      c(6) = max(z);
+    end
+  end
+  ax([1 3 5]) = min(ax([1 3 5]), c([1 3 5]));
+  ax([2 4 6]) = max(ax([2 4 6]), c([2 4 6]));
+end
+if strcmp(get(gca,'xscale'), 'log')
+  ax([1 2]) = log(ax([1 2]));
+end
+if strcmp(get(gca,'yscale'), 'log')
+  ax([3 4]) = log(ax([3 4]));
+end
+dx = ax(2)-ax(1);
+if dx == 0
+  dx = 1;
+end
+dy = ax(4)-ax(3);
+if dy == 0
+  dy = 1;
+end
+dz = ax(6)-ax(5);
+if dz == 0
+  dz = 1;
+end
+ax = ax + [-dx dx -dy dy -dz dz]*pct;
+if strcmp(get(gca,'xscale'), 'log')
+  ax([1 2]) = exp(ax([1 2]));
+end
+if strcmp(get(gca,'yscale'), 'log')
+  ax([3 4]) = exp(ax([3 4]));
+end
+% clip for 2D
+ax = ax(1:length(axis));
+axis(ax);
+if nargout < 1
+  clear ax
+end
diff --git a/sourcecodes/bnt-master/KPMtools/bipartiteMatchingDemo.m b/sourcecodes/bnt-master/KPMtools/bipartiteMatchingDemo.m
new file mode 100644
index 00000000..112547be
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/bipartiteMatchingDemo.m
@@ -0,0 +1,112 @@
+% Consider matching sources to detections
+
+%  s1 d2  
+%         s2 d3
+%  d1
+
+%a  = bipartiteMatchingHungarian([52;0.01])
+
+% sources(:,i) = [x y] coords
+sources = [0.1 0.7; 0.6 0.4]';
+detections = [0.2 0.2; 0.2 0.8; 0.7 0.1]';
+dst = sqdist(sources, detections);
+
+% a = [2 3] which means s1-d2, s2-d3
+a = bipartiteMatchingHungarian(dst);
+a2 = bipartiteMatchingIntProg(dst);
+assert(isequal(a(:),a2(:)))
+
+
+figure(1); clf
+bipartiteMatchingDemoPlot(sources, detections, a)
+
+
+
+
+%%%% Flip roles of sources and detections
+
+%dst  = dst';
+dst = sqdist(detections, sources);
+% a = [0 1 2] which means d1-0, d2-s1, d3-s2
+a = bipartiteMatchingHungarian(dst);
+
+a2 = bipartiteMatchingIntProg(dst);
+assert(isequal(a(:),a2(:)))
+
+figure(2); clf
+bipartiteMatchingDemoPlot(detections, sources, a) % swapped args
+
+
+
+
+%%%%%%%%%% Move s1 nearer to d1
+%  d2  
+%         s2 d3
+%  s1 d1
+
+sources = [0.1 0.3; 0.6 0.4]';
+detections = [0.2 0.2; 0.2 0.8; 0.7 0.1]';
+dst = sqdist(sources, detections);
+
+% a = [2 3] which means s1-d2, s2-d3
+a = bipartiteMatchingHungarian(dst);
+[a2, ass] = bipartiteMatchingIntProg(dst);
+assert(isequal(a(:),a2(:)))
+
+
+figure(3); clf
+bipartiteMatchingDemoPlot(sources, detections, a)
+
+
+
+%%%%%%%%%%
+
+% Use random points
+
+% Generate 2D data from a mixture of 2 Gaussians (from netlab demgmm1)
+randn('state', 0); rand('state', 0);
+gmix = gmm(2, 2, 'spherical');
+ndat1 = 10; ndat2 = 10; ndata = ndat1+ndat2;
+%gmix.centres =  [0.3 0.3; 0.7 0.7]; 
+%gmix.covars = [0.01 0.01];
+gmix.centres =  [0.5 0.5; 0.5 0.5];
+gmix.covars = [0.1 0.01];
+[x, label] = gmmsamp(gmix, ndata);
+
+ndx = find(label==1);
+sources = x(ndx,:)';
+ndx = find(label==2);
+detections = x(ndx,:)';
+dst = sqdist(sources, detections);
+
+[a, ass] = bipartiteMatchingIntProg(dst);
+[a2] = bipartiteMatchingHungarian(dst);
+assert(isequal(a(:), a2(:)))
+
+figure(4); clf
+bipartiteMatchingDemoPlot(sources, detections, a)
+
+% only match 80% of points
+p1 = size(sources, 2);
+p2 = size(detections, 2);
+nmatch = ceil(0.8*min(p1,p2));
+a2 = bipartiteMatchingIntProg(dst, nmatch);
+figure(5); clf
+bipartiteMatchingDemoPlot(sources, detections, a2)
+
+
+%%% swap roles
+
+ndx = find(label==2);
+sources = x(ndx,:)';
+ndx = find(label==1);
+detections = x(ndx,:)';
+dst = sqdist(sources, detections);
+
+% only match 80% of points
+p1 = size(sources, 2);
+p2 = size(detections, 2);
+nmatch = ceil(0.8*min(p1,p2));
+a2 = bipartiteMatchingIntProg(dst, nmatch);
+figure(6); clf
+bipartiteMatchingDemoPlot(sources, detections, a2)
diff --git a/sourcecodes/bnt-master/KPMtools/bipartiteMatchingDemoPlot.m b/sourcecodes/bnt-master/KPMtools/bipartiteMatchingDemoPlot.m
new file mode 100644
index 00000000..1c9388c1
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/bipartiteMatchingDemoPlot.m
@@ -0,0 +1,24 @@
+function bipartiteMatchingDemoPlot(sources, detections, a)
+
+hold on
+p1 = size(sources,2);
+p2 = size(detections,2);
+for i=1:p1
+  h=text(sources(1,i), sources(2,i), sprintf('s%d', i));
+  set(h, 'color', 'r');
+end
+for i=1:p2
+  h=text(detections(1,i), detections(2,i), sprintf('d%d', i));
+  set(h, 'color', 'b');
+end
+
+if nargin < 3, return; end
+
+for i=1:p1
+  j = a(i);
+  if j==0 % i not matched to anything
+    continue
+  end
+  line([sources(1,i) detections(1,j)], [sources(2,i) detections(2,j)])
+end
+axis_pct;
diff --git a/sourcecodes/bnt-master/KPMtools/bipartiteMatchingHungarian.m b/sourcecodes/bnt-master/KPMtools/bipartiteMatchingHungarian.m
new file mode 100644
index 00000000..a794ba02
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/bipartiteMatchingHungarian.m
@@ -0,0 +1,90 @@
+% MATCH - Solves the weighted bipartite matching (or assignment)
+%         problem.
+%
+% Usage:  a = match(C);
+%
+% Arguments:   
+%         C     - an m x n cost matrix; the sets are taken to be
+%                 1:m and 1:n; C(i, j) gives the cost of matching
+%                 items i (of the first set) and j (of the second set)
+%
+% Returns:
+%
+%         a     - an m x 1 assignment vector, which gives the
+%                 minimum cost assignment.  a(i) is the index of
+%                 the item of 1:n that was matched to item i of
+%                 1:m.  If item i (of 1:m) was not matched to any 
+%                 item of 1:n, then a(i) is zero.
+
+% Copyright (C) 2002 Mark A. Paskin
+%
+% This program is free software; you can redistribute it and/or modify
+% it under the terms of the GNU General Public License as published by
+% the Free Software Foundation; either version 2 of the License, or
+% (at your option) any later version.
+%
+% This program is distributed in the hope that it will be useful, but
+% WITHOUT ANY WARRANTY; without even the implied warranty of
+% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+% General Public License for more details.
+%
+% You should have received a copy of the GNU General Public License
+% along with this program; if not, write to the Free Software
+% Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+% USA.
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+function [a] = optimalMatching(C)
+
+% Trivial cases:
+[p, q] = size(C);
+if (p == 0)
+  a = []; 
+  return;
+elseif (q == 0)
+  a = zeros(p, 1);
+  return;
+end
+
+
+if  0
+% First, reduce the problem by making easy optimal matches.  If two
+% elements agree that they are the best match, then match them up.
+[x, a] = min(C, [], 2);
+[y, b] = min(C, [], 1);
+u = find(1:p ~= b(a(:)));
+a(u) = 0;
+v = find(1:q ~= a(b(:))');
+C = C(u, v);
+if (isempty(C)) return; end
+end
+
+% Get the (new) size of the two sets, u and v.
+[m, n] = size(C);
+
+%mx = realmax;
+mx = 2*max(C(:));
+mn = -2*min(C(:));
+% Pad the affinity matrix to be square
+if (m < n)
+  C = [C; mx * ones(n - m, n)];
+elseif (n < m)
+  C = [C, mx * ones(m, m - n)];
+end
+
+% Run the Hungarian method.  First replace infinite values by the
+% largest (or smallest) finite values.
+C(find(isinf(C) & (C > 0))) = mx;
+C(find(isinf(C) & (C < 0))) = mn;
+%fprintf('running hungarian\n');
+[b, cost] = hungarian(C');
+
+% Extract only the real assignments
+ap = b(1:m)';
+ap(find(ap > n)) = 0;
+
+a = ap; 
+%% Incorporate this sub-assignment into the complete assignment
+%  k = find(ap);
+%  a(u(k)) = v(ap(k));
+
diff --git a/sourcecodes/bnt-master/KPMtools/bipartiteMatchingIntProg.m b/sourcecodes/bnt-master/KPMtools/bipartiteMatchingIntProg.m
new file mode 100644
index 00000000..26efaba8
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/bipartiteMatchingIntProg.m
@@ -0,0 +1,69 @@
+function [a,ass] = bipartiteMatchingIntProg(dst, nmatches)
+% BIPARTITEMATCHINGINTPROG Use binary integer programming (linear objective) to solve for optimal linear assignment
+% function a = bipartiteMatchingIntProg(dst)
+% a(i) = best matching column for row i
+% 
+% This gives the same result as bipartiteMatchingHungarian.
+%
+% function a = bibpartiteMatchingIntProg(dst, nmatches)
+% only matches the specified number (must be <= min(size(dst))).
+% This can be used to allow outliers in both source and target.
+%
+% For details, see Marciel & Costeira, "A global solution to sparse correspondence
+% problems", PAMI 25(2), 2003
+
+if nargin < 2, nmatches = []; end
+
+[p1 p2] = size(dst);
+p1orig = p1; p2orig = p2;
+dstorig = dst;
+
+if isempty(nmatches) % no outliers allowed  (modulo size difference)
+  % ensure matrix is square
+  m = max(dst(:));
+  if p1<p2
+    dst = [dst; m*ones(p2-p1, p2)];
+  elseif p1>p2
+    dst = [dst  m*ones(p1, p1-p2)];
+  end
+end
+[p1 p2] = size(dst);
+
+
+c = dst(:); % vectorize cost matrix
+
+% row-sum: ensure each column sums to 1
+A2 = kron(eye(p2), ones(1,p1));
+b2 = ones(p2,1);
+
+% col-sum: ensure each row sums to 1
+A3 = kron(ones(1,p2), eye(p1));
+b3 = ones(p1,1);
+
+if isempty(nmatches)
+  % enforce doubly  stochastic
+  A = [A2; A3];
+  b = [b2; b3];
+  Aineq = zeros(1, p1*p2);
+  bineq = 0;
+else
+  nmatches = min([nmatches, p1, p2]);
+  Aineq = [A2; A3];
+  bineq = [b2; b3]; % row and col sums <= 1
+  A = ones(1,p1*p2);
+  b = nmatches; % total num matches = b (otherwise get degenerate soln)
+end
+
+
+ass = bintprog(c, Aineq, bineq, A, b);
+ass = reshape(ass, p1, p2);
+
+a = zeros(1, p1orig);
+for i=1:p1orig
+  ndx = find(ass(i,:)==1);
+  if ~isempty(ndx) & (ndx <= p2orig)
+    a(i) = ndx;
+  end
+end
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/block.m b/sourcecodes/bnt-master/KPMtools/block.m
new file mode 100644
index 00000000..9a4728bc
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/block.m
@@ -0,0 +1,15 @@
+function sub = block(blocks, block_sizes)
+% BLOCK Return a vector of subscripts corresponding to the specified blocks.
+% sub = block(blocks, block_sizes)
+% 
+% e.g., block([2 5], [2 1 2 1 2]) = [3 7 8].
+
+blocks = blocks(:)';
+block_sizes = block_sizes(:)';
+skip = [0 cumsum(block_sizes)];
+start = skip(blocks)+1;
+fin = start + block_sizes(blocks) - 1;
+sub = [];
+for j=1:length(blocks)
+  sub = [sub start(j):fin(j)];
+end
diff --git a/sourcecodes/bnt-master/KPMtools/cell2matPad.m b/sourcecodes/bnt-master/KPMtools/cell2matPad.m
new file mode 100644
index 00000000..5b9e94a1
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/cell2matPad.m
@@ -0,0 +1,22 @@
+function data2 = cell2matPad(data)
+% data{f}(y,x,b) - each frame can have a different size (can can even be empty)
+% data2(y,x,b,f) = zero padded version
+
+Nframes = length(data);
+Nbands = -inf;
+nr = -inf; nc = -inf;
+for f=1:Nframes
+  if isempty(data{f}), continue; end
+  nr = max(nr, size(data{f},1));
+  nc = max(nc, size(data{f},2));
+  Nbands = max(Nbands, size(data{f},3));
+end    
+data2 = zeros(nr, nc, Nbands, Nframes);
+for f=1:Nframes
+  if isempty(data{f}), continue; end
+  data2(1:size(data{f},1), 1:size(data{f},2), :, f) = data{f};
+end
+if Nbands == 1
+  data2 = squeeze(data2); % reshape(data2, [size(data2,1), size(data2,2), Nframes]);
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/cell2num.m b/sourcecodes/bnt-master/KPMtools/cell2num.m
new file mode 100644
index 00000000..ffd25ce9
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/cell2num.m
@@ -0,0 +1,57 @@
+function N = cell2num(C)
+% CELL2NUM Convert a 2D cell array to a 2D numeric array 
+% N = cell2num(C)
+% If the cells contain column vectors, they must have the same number of rows in each row of C.
+% Each column will be concatenated.
+%
+% Example 1:
+% C = num2cell(rand(2,2))
+%    [0.4565]    [0.8214]
+%    [0.0185]    [0.4447]
+% N = cell2num(C)
+%     0.4565    0.8214
+%     0.0185    0.4447
+%
+% Example 2:
+% C = cell(2, 3);
+% for i=1:2
+%   for j=1:3
+%     C{i,j} = rand(i, 1);
+%   end
+% end
+% C = 
+%     [    0.8998]    [    0.8216]    [    0.6449]
+%     [2x1 double]    [2x1 double]    [2x1 double]
+% C{2,1} = 
+%     0.8180
+%     0.6602
+% N=cell2num(C)
+%     0.8998    0.8216    0.6449
+%     0.8180    0.3420    0.3412
+%     0.6602    0.2897    0.5341
+
+
+%  error('use cell2mat in matlab 7')
+
+
+if isempty(C)
+  N = [];
+  return;
+end
+
+if any(cellfun('isempty', C)) %any(isemptycell(C))
+  error('can''t convert cell array with empty cells to matrix')
+end
+
+[nrows ncols] = size(C);
+%N = reshape(cat(1, C{:}), [nrows ncols]); % this only works if C only contains scalars
+r = 0;
+for i=1:nrows
+  r = r + size(C{i,1}, 1);
+end
+c = 0;
+for j=1:ncols
+  c = c + size(C{1,j}, 2);
+end
+N = reshape(cat(1, C{:}), [r c]);
+
diff --git a/sourcecodes/bnt-master/KPMtools/centeringMatrix.m b/sourcecodes/bnt-master/KPMtools/centeringMatrix.m
new file mode 100644
index 00000000..92623a0d
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/centeringMatrix.m
@@ -0,0 +1,8 @@
+N = 3;
+x = rand(N,2); % each row is a feature vector 
+m = mean(x,1);
+xc = x-repmat(m, N, 1);
+
+C = eye(N) - (1/N)*ones(N,N);
+xc2 = C*x;
+assert(approxeq(xc, xc2))
diff --git a/sourcecodes/bnt-master/KPMtools/checkpsd.m b/sourcecodes/bnt-master/KPMtools/checkpsd.m
new file mode 100644
index 00000000..cbd35203
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/checkpsd.m
@@ -0,0 +1,15 @@
+function s = checkpsd(s)
+
+if (any(isnan(s) | isinf(s) | ~isreal(s)))
+  warning('S contains complex numbers, Inf, or NaN'); 
+end
+% Drop any negative eigenvalues.
+[V, D] = eig(full(s));
+d = real(diag(D));
+if (any(d < 0))
+  warning(sprintf(['S is not positive semidefinite (min. eig. =' ...
+		   ' %0.5g); projecting.'], min(d)));
+  d(find(d < 0)) = 0;
+  D = diag(d);
+  s = V * D * V';
+end
diff --git a/sourcecodes/bnt-master/KPMtools/chi2inv.m b/sourcecodes/bnt-master/KPMtools/chi2inv.m
new file mode 100644
index 00000000..90c60258
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/chi2inv.m
@@ -0,0 +1,36 @@
+function x = chi2inv(p,v);
+%CHI2INV Inverse of the chi-square cumulative distribution function (cdf).
+%   X = CHI2INV(P,V)  returns the inverse of the chi-square cdf with V  
+%   degrees of freedom at the values in P. The chi-square cdf with V 
+%   degrees of freedom, is the gamma cdf with parameters V/2 and 2.   
+%
+%   The size of X is the common size of P and V. A scalar input
+%   functions as a constant matrix of the same size as the other input.   
+
+%   References:
+%      [1]  M. Abramowitz and I. A. Stegun, "Handbook of Mathematical
+%      Functions", Government Printing Office, 1964, 26.4.
+%      [2] E. Kreyszig, "Introductory Mathematical Statistics",
+%      John Wiley, 1970, section 10.2 (page 144)
+
+%   Copyright 1993-2002 The MathWorks, Inc. 
+%   $Revision: 1.1.1.1 $  $Date: 2005/04/26 02:30:30 $
+
+if nargin < 2, 
+    error('Requires two input arguments.');
+end
+
+[errorcode p v] = distchck(2,p,v);
+
+if errorcode > 0
+    error('Requires non-scalar arguments to match in size.');
+end
+
+% Call the gamma inverse function. 
+x = gaminv(p,v/2,2);
+
+% Return NaN if the degrees of freedom is not positive.
+k = (v <= 0);
+if any(k(:))
+    x(k) = NaN;
+end
diff --git a/sourcecodes/bnt-master/KPMtools/choose.m b/sourcecodes/bnt-master/KPMtools/choose.m
new file mode 100644
index 00000000..32540548
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/choose.m
@@ -0,0 +1,5 @@
+function c = choose(n,k)
+% CHOOSE The number of ways of choosing k things from n 
+% c = choose(n,k)
+
+c = factorial(n)/(factorial(k) * factorial(n-k));      
diff --git a/sourcecodes/bnt-master/KPMtools/collapse_mog.m b/sourcecodes/bnt-master/KPMtools/collapse_mog.m
new file mode 100644
index 00000000..2fe6436f
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/collapse_mog.m
@@ -0,0 +1,22 @@
+function [new_mu, new_Sigma, new_Sigma2] = collapse_mog(mu, Sigma, coefs)
+% COLLAPSE_MOG Collapse a mixture of Gaussians to a single Gaussian by moment matching
+% [new_mu, new_Sigma] = collapse_mog(mu, Sigma, coefs)
+%
+% coefs(i) - weight of i'th mixture component
+% mu(:,i), Sigma(:,:,i) - params of i'th mixture component
+
+% S = sum_c w_c (S_c + m_c m_c' + m m' - 2 m_c m') 
+%   = sum_c w_c (S_c + m_c m_c') + m m' - 2 (sum_c m_c) m'
+%   = sum_c w_c (S_c + m_c m_c') - m m'
+
+new_mu = sum(mu * diag(coefs), 2); % weighted sum of columns
+
+n = length(new_mu);
+new_Sigma = zeros(n,n);
+new_Sigma2 = zeros(n,n);
+for j=1:length(coefs)
+  m = mu(:,j) - new_mu;
+  new_Sigma = new_Sigma + coefs(j) * (Sigma(:,:,j) + m*m');
+  new_Sigma2 = new_Sigma2 + coefs(j) * (Sigma(:,:,j) + mu(:,j)*mu(:,j)');
+end
+%assert(approxeq(new_Sigma, new_Sigma2 - new_mu*new_mu'))
diff --git a/sourcecodes/bnt-master/KPMtools/colmult.c b/sourcecodes/bnt-master/KPMtools/colmult.c
new file mode 100644
index 00000000..e9d5008c
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/colmult.c
@@ -0,0 +1,62 @@
+#include <stdio.h>
+#include "mex.h"
+
+/*
+out = colop(M, v)
+
+Apply binary operator to a vector v and to each column of M in turn
+to produce a matrix the same size as M.
+
+This is equivalent to
+
+out = zeros(size(M));
+for col=1:size(M,2)
+  out(:,col) = op(M(:,col), v);
+end
+
+The code needs to be modified for each different operator 'op'.
+eg op = '.*'
+
+In vectorized form:
+
+out = M .* repmat(v(:), 1, size(M,2))
+
+(This function was formerly called repmat_and_mult.c)
+
+*/
+
+/* M(i,j) = M(i + nrows*j) since Matlab uses Fortran layout. */
+
+ 
+#define INMAT(i,j) M[(i)+nrows*(j)]
+#define OUTMAT(i,j) out[(i)+nrows*(j)]
+
+void mexFunction(
+                 int nlhs,       mxArray *plhs[],
+                 int nrhs, const mxArray *prhs[]
+		 )
+{
+  double *out, *M, *v;
+  int nrows, ncols, r, c;
+  
+  /* read the input args */
+  M = mxGetPr(prhs[0]);
+  nrows = mxGetM(prhs[0]);
+  ncols = mxGetN(prhs[0]);
+
+  v = mxGetPr(prhs[1]);
+
+  plhs[0] = mxCreateDoubleMatrix(nrows, ncols, mxREAL);
+  out = mxGetPr(plhs[0]); 
+
+  for (c=0; c < ncols; c++) {
+    for (r=0; r < nrows; r++) {
+      OUTMAT(r,c) = INMAT(r,c) * v[r]; 
+      /* printf("r=%d, c=%d, M=%f, v=%f\n", r, c, INMAT(r,c), v[r]);  */
+    }
+  }
+
+}
+
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/computeROC.m b/sourcecodes/bnt-master/KPMtools/computeROC.m
new file mode 100644
index 00000000..3b35332c
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/computeROC.m
@@ -0,0 +1,64 @@
+function [FPrate, TPrate, AUC, thresholds] = computeROC(confidence, testClass)
+% function [FPrate, TPrate, AUC, thresholds] = computeROC(confidence, testClass)
+%
+% computeROC computes the data for an ROC curve based on a classifier's confidence output.
+% It returns the false positive rate and the true positive rate along with
+% the area under the ROC curve, and the list of thresholds.
+%
+% Inputs: 
+%           - confidence(i) is proportional to the probability that
+%             testClass(i) is positive
+%
+% testClass = 0 => target absent
+% testClass = 1 => target present
+%
+% Based on algorithms 2 and 4 from Tom Fawcett's paper "ROC Graphs: Notes and
+% Practical Considerations for Data Mining Researchers" (2003)
+% http://www.hpl.hp.com/techreports/2003/HPL-2003-4.pdf"
+%
+% Vlad Magdin, 21 Feb 2005
+
+% break ties in scores
+S = rand('state');
+rand('state',0);
+confidence = confidence + rand(size(confidence))*10^(-10);
+rand('state',S)
+[thresholds order] = sort(confidence, 'descend');
+testClass = testClass(order);
+
+%%% -- calculate TP/FP rates and totals -- %%%
+AUC = 0;
+faCnt = 0;
+tpCnt = 0;
+falseAlarms = zeros(1,size(thresholds,2));
+detections = zeros(1,size(thresholds,2));
+fPrev = -inf;
+faPrev = 0;
+tpPrev = 0;
+
+P = max(size(find(testClass==1)));
+N = max(size(find(testClass==0)));
+
+for i=1:length(thresholds)
+    if thresholds(i) ~= fPrev
+        falseAlarms(i) = faCnt;
+        detections(i) = tpCnt;
+
+        AUC = AUC + polyarea([faPrev faPrev faCnt/N faCnt/N],[0 tpPrev tpCnt/P 0]);
+
+        fPrev = thresholds(i);
+        faPrev = faCnt/N;
+        tpPrev = tpCnt/P;
+    end
+    
+    if testClass(i) == 1
+        tpCnt = tpCnt + 1;
+    else
+        faCnt = faCnt + 1;
+    end
+end
+
+AUC = AUC + polyarea([faPrev faPrev 1 1],[0 tpPrev 1 0]);
+
+FPrate = falseAlarms/N;
+TPrate = detections/P;
diff --git a/sourcecodes/bnt-master/KPMtools/compute_counts.m b/sourcecodes/bnt-master/KPMtools/compute_counts.m
new file mode 100644
index 00000000..d710bfcb
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/compute_counts.m
@@ -0,0 +1,17 @@
+function count = compute_counts(data, sz)
+% COMPUTE_COUNTS Count the number of times each combination of discrete assignments occurs
+% count = compute_counts(data, sz)
+%
+% data(i,t) is the value of variable i in case t
+% sz(i) : values for variable i are assumed to be in [1:sz(i)]
+%
+% Example: to compute a transition matrix for an HMM from a sequence of labeled states:
+% transmat = mk_stochastic(compute_counts([seq(1:end-1); seq(2:end)], [nstates nstates]));
+
+assert(length(sz) == size(data, 1));
+P = prod(sz);
+indices = subv2ind(sz, data'); % each row of data' is a case 
+%count = histc(indices, 1:P);
+count = hist(indices, 1:P);
+count = myreshape(count, sz);
+
diff --git a/sourcecodes/bnt-master/KPMtools/conf2mahal.m b/sourcecodes/bnt-master/KPMtools/conf2mahal.m
new file mode 100644
index 00000000..8e96dd18
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/conf2mahal.m
@@ -0,0 +1,62 @@
+% CONF2MAHAL - Translates a confidence interval to a Mahalanobis
+%              distance.  Consider a multivariate Gaussian
+%              distribution of the form
+%
+%   p(x) = 1/sqrt((2 * pi)^d * det(C)) * exp((-1/2) * MD(x, m, inv(C)))
+%
+%              where MD(x, m, P) is the Mahalanobis distance from x
+%              to m under P:
+%
+%                 MD(x, m, P) = (x - m) * P * (x - m)'
+%
+%              A particular Mahalanobis distance k identifies an
+%              ellipsoid centered at the mean of the distribution.
+%              The confidence interval associated with this ellipsoid
+%              is the probability mass enclosed by it.  Similarly,
+%              a particular confidence interval uniquely determines
+%              an ellipsoid with a fixed Mahalanobis distance.
+%
+%              If X is an d dimensional Gaussian-distributed vector,
+%              then the Mahalanobis distance of X is distributed
+%              according to the Chi-squared distribution with d
+%              degrees of freedom.  Thus, the Mahalanobis distance is
+%              determined by evaluating the inverse cumulative
+%              distribution function of the chi squared distribution
+%              up to the confidence value.
+%
+% Usage:
+% 
+%   m = conf2mahal(c, d);
+%
+% Inputs:
+%
+%   c    - the confidence interval
+%   d    - the number of dimensions of the Gaussian distribution
+%
+% Outputs:
+%
+%   m    - the Mahalanobis radius of the ellipsoid enclosing the
+%          fraction c of the distribution's probability mass
+%
+% See also: MAHAL2CONF
+
+% Copyright (C) 2002 Mark A. Paskin
+%
+% This program is free software; you can redistribute it and/or modify
+% it under the terms of the GNU General Public License as published by
+% the Free Software Foundation; either version 2 of the License, or
+% (at your option) any later version.
+%
+% This program is distributed in the hope that it will be useful, but
+% WITHOUT ANY WARRANTY; without even the implied warranty of
+% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+% General Public License for more details.
+%
+% You should have received a copy of the GNU General Public License
+% along with this program; if not, write to the Free Software
+% Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+% USA.
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+function m = conf2mahal(c, d)
+
+m = chi2inv(c, d);
\ No newline at end of file
diff --git a/sourcecodes/bnt-master/KPMtools/cross_entropy.m b/sourcecodes/bnt-master/KPMtools/cross_entropy.m
new file mode 100644
index 00000000..1a7d2003
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/cross_entropy.m
@@ -0,0 +1,15 @@
+function kl = cross_entropy(p, q, symmetric)
+% CROSS_ENTROPY Compute the Kullback-Leibler divergence between two discrete prob. distributions
+% kl = cross_entropy(p, q, symmetric)
+%
+% If symmetric = 1, we compute the symmetric version. Default: symmetric = 0;
+
+tiny = exp(-700);
+if nargin < 3, symmetric = 0; end
+p = p(:);
+q = q(:);
+if symmetric
+  kl  = (sum(p .* log((p+tiny)./(q+tiny))) + sum(q .* log((q+tiny)./(p+tiny))))/2;
+else
+  kl  = sum(p .* log((p+tiny)./(q+tiny)));
+end                                           
diff --git a/sourcecodes/bnt-master/KPMtools/dirKPM.m b/sourcecodes/bnt-master/KPMtools/dirKPM.m
new file mode 100644
index 00000000..39157137
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/dirKPM.m
@@ -0,0 +1,98 @@
+function filenames = dirKPM(dirname, ext, varargin)
+% dirKPM Like the built-in dir command, but returns filenames as a cell array instead of a struct
+%
+% filenames = dirKPM(dirname)
+% returns all files, except '.' and '..'
+%
+% filenames = dirKPM('images', '*.jpg')
+% returns files with this extension
+%   eg filenames{1} = 'foo.jpg' etc
+%
+% OPTIONAL ARGUMENTS [default in brackets]
+% filenames = dirKPM('images', '', param1, val1, param2, val2, ...)
+%
+% 'fileType'='image' ['all'] means return files with extension .jpg, .png, .bmp
+%
+% 'prepend'=1 [0] means preprend folder name to filename
+%    eg filenames{1} = 'images/foo.jpg'
+%
+% 'doSort'=1 [1] means sort filenames in ascending alphanumerical order (where possible)
+%
+% 'doRecurse'=1 [0] recursive dir, apply the same dirKPM call on all
+% subfolders (decrease MAXDEPTH option to prevent recursion from branching
+% too explosively)
+
+if nargin < 1, dirname = '.'; end
+
+if nargin < 2, ext = ''; end
+
+[fileType, prepend, doSort, doRecurse, MAXDEPTH, DEPTH] = process_options(...
+	varargin, 'fileType', 'all', 'prepend', 0, 'doSort', 1, 'doRecurse', 0,...
+	'MAXDEPTH', 3, 'DEPTH', 0);
+
+tmp = dir(fullfile(dirname, ext));
+[filenames I] = setdiff({tmp.name}, {'.', '..'});
+tmp = tmp(I);
+
+if doRecurse && sum([tmp.isdir])>0 && DEPTH<MAXDEPTH
+	for fi=1:length(tmp)
+		subDirFilenames = {};
+
+		if tmp(fi).isdir
+			varargin = change_option( varargin, 'prepend', false );
+			varargin = change_option( varargin, 'doSort', false );
+			varargin = change_option( varargin, 'DEPTH', DEPTH+1 );
+			subDirFilenames = dirKPM( fullfile(dirname,tmp(fi).name), ext, varargin{:} );
+
+			for sdfi=1:length(subDirFilenames)
+				subDirFilenames{sdfi} = fullfile(tmp(fi).name, subDirFilenames{sdfi});
+			end
+		end
+
+
+		nfilenames = length(filenames);
+		if length(subDirFilenames)>0
+			filenames(nfilenames+1:nfilenames+length(subDirFilenames)) = subDirFilenames;
+		end
+	end
+end
+
+nfiles = length(filenames);
+if nfiles==0 return; end
+
+switch fileType
+	case 'image',
+		for fi=1:nfiles
+			good(fi) = isImage(filenames{fi});
+		end
+		filenames = filenames(find(good));
+	case 'all',
+		% no-op
+	otherwise
+		error(sprintf('unrecognized file type %s', fileType));
+end
+
+if doSort
+% 	% sort filenames alphanumerically (if possible)
+%  DJE, buggy, MUST save tmp.anr/snr/str or else we potentially lose
+%  filenames
+% 	tmp = asort(filenames, '-s', 'ascend');
+% 	if ~isempty(tmp.anr)
+% 		filenames = tmp.anr';
+% 	else
+% 		filenames = tmp.str';
+% 	end
+	% if names could not be sorted, return original order
+
+	filenames=sort(filenames);
+	
+end
+
+
+if prepend
+	nfiles = length(filenames);
+	for fi=1:nfiles
+		filenames{fi} = fullfile(dirname, filenames{fi});
+	end
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/div.m b/sourcecodes/bnt-master/KPMtools/div.m
new file mode 100644
index 00000000..a76bc503
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/div.m
@@ -0,0 +1,5 @@
+function d = div(a,b)
+% DIV Integer division
+% d = div(a,b)
+
+d = floor(a / b);        
diff --git a/sourcecodes/bnt-master/KPMtools/draw_circle.m b/sourcecodes/bnt-master/KPMtools/draw_circle.m
new file mode 100644
index 00000000..5d60077d
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/draw_circle.m
@@ -0,0 +1,28 @@
+function h = draw_circle(x, r, outline_color, fill_color)
+% draw filled circles at centers x with radii r.
+% x is a matrix of columns.  r is a row vector.
+
+n = 40;					% resolution
+radians = [0:(2*pi)/(n-1):2*pi];
+unitC = [sin(radians); cos(radians)];
+
+% extend r if necessary
+if length(r) < cols(x)
+  r = [r repmat(r(length(r)), 1, cols(x)-length(r))];
+end
+
+h = [];
+% hold is needed for fill()
+held = ishold;
+hold on
+for i=1:cols(x)
+  y = unitC*r(i) + repmat(x(:, i), 1, n);
+  if nargin < 4
+    h = [h line(y(1,:), y(2,:), 'Color', outline_color)];
+  else
+    h = [h fill(y(1,:), y(2,:), fill_color, 'EdgeColor', outline_color)];
+  end
+end
+if ~held
+  hold off
+end
diff --git a/sourcecodes/bnt-master/KPMtools/draw_ellipse.m b/sourcecodes/bnt-master/KPMtools/draw_ellipse.m
new file mode 100644
index 00000000..4effef0f
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/draw_ellipse.m
@@ -0,0 +1,24 @@
+function h = draw_ellipse(x, c, outline_color, fill_color)
+% DRAW_ELLIPSE(x, c, outline_color, fill_color)
+%   Draws ellipses at centers x with covariance matrix c.
+%   x is a matrix of columns.  c is a positive definite matrix.
+%   outline_color and fill_color are optional.
+
+n = 40;					% resolution
+radians = [0:(2*pi)/(n-1):2*pi];
+unitC = [sin(radians); cos(radians)];
+r = chol(c)';
+
+if nargin < 3
+  outline_color = 'g';
+end
+
+h = [];
+for i=1:cols(x)
+  y = r*unitC + repmat(x(:, i), 1, n);
+  if nargin < 4
+    h = [h line(y(1,:), y(2,:), 'Color', outline_color)];
+  else
+    h = [h fill(y(1,:), y(2,:), fill_color, 'EdgeColor', outline_color)];
+  end
+end
diff --git a/sourcecodes/bnt-master/KPMtools/draw_ellipse_axes.m b/sourcecodes/bnt-master/KPMtools/draw_ellipse_axes.m
new file mode 100644
index 00000000..f6c44504
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/draw_ellipse_axes.m
@@ -0,0 +1,19 @@
+function h = draw_ellipse_axes(x, c, linespec)
+% DRAW_ELLIPSE_AXES(x, c, linespec)
+%   Draws the major and minor axes of ellipses.
+%   Ellipses are centered at x with covariance matrix c.
+%   x is a matrix of columns.  c is a positive definite matrix.
+%   linespec is optional.
+
+[v,e] = eig(c);
+v = v*sqrt(e);
+
+h = [];
+for j = 1:cols(v)
+  x1 = repmat(x(1,:),2,1) + repmat([-1;1]*v(1,j),1,cols(x));
+  x2 = repmat(x(2,:),2,1) + repmat([-1;1]*v(2,j),1,cols(x));
+  h = [h line(x1,x2)];
+end
+if nargin > 2
+  set_linespec(h,linespec);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/em_converged.m b/sourcecodes/bnt-master/KPMtools/em_converged.m
new file mode 100644
index 00000000..2b2919e2
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/em_converged.m
@@ -0,0 +1,32 @@
+function [converged, decrease] = em_converged(loglik, previous_loglik, threshold, check_increased)
+% EM_CONVERGED Has EM converged?
+% [converged, decrease] = em_converged(loglik, previous_loglik, threshold)
+%
+% We have converged if the slope of the log-likelihood function falls below 'threshold', 
+% i.e., |f(t) - f(t-1)| / avg < threshold,
+% where avg = (|f(t)| + |f(t-1)|)/2 and f(t) is log lik at iteration t.
+% 'threshold' defaults to 1e-4.
+%
+% This stopping criterion is from Numerical Recipes in C p423
+%
+% If we are doing MAP estimation (using priors), the likelihood can decrase,
+% even though the mode of the posterior is increasing.
+
+if nargin < 3, threshold = 1e-4; end
+if nargin < 4, check_increased = 1; end
+
+converged = 0;
+decrease = 0;
+
+if check_increased
+  if loglik - previous_loglik < -1e-3 % allow for a little imprecision
+    fprintf(1, '******likelihood decreased from %6.4f to %6.4f!\n', previous_loglik, loglik);
+    decrease = 1;
+converged = 0;
+return;
+  end
+end
+
+delta_loglik = abs(loglik - previous_loglik);
+avg_loglik = (abs(loglik) + abs(previous_loglik) + eps)/2;
+if (delta_loglik / avg_loglik) < threshold, converged = 1; end
diff --git a/sourcecodes/bnt-master/KPMtools/entropy.m b/sourcecodes/bnt-master/KPMtools/entropy.m
new file mode 100644
index 00000000..d879cc48
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/entropy.m
@@ -0,0 +1,17 @@
+function H = entropy(v, scale)
+% ENTROPY Entropy log base 2
+% H = entropy(v)
+% If v is a matrix, we compute the entropy of each column
+%
+% % H = entropy(v,1) means we scale the result so that it lies in [0,1]
+
+if nargin < 2, scale = 0; end
+
+v = v + (v==0);
+H = -1 * sum(v .* log2(v), 1); % sum the rows
+
+if scale
+  n = size(v, 1);
+  unif = normalise(ones(n,1));
+  H = H / entropy(unif);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/exportfig.m b/sourcecodes/bnt-master/KPMtools/exportfig.m
new file mode 100644
index 00000000..069146f3
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/exportfig.m
@@ -0,0 +1,991 @@
+function varargout = exportfig(varargin)
+%EXPORTFIG  Export a figure.
+%   EXPORTFIG(H, FILENAME) writes the figure H to FILENAME.  H is
+%   a figure handle and FILENAME is a string that specifies the
+%   name of the output file.
+%
+%   EXPORTFIG(H, FILENAME, OPTIONS) writes the figure H to FILENAME
+%   with options initially specified by the structure OPTIONS. The
+%   field names of OPTIONS must be legal parameters listed below
+%   and the field values must be legal values for the corresponding
+%   parameter. Default options can be set in releases prior to R12
+%   by storing the OPTIONS structure in the root object's appdata
+%   with the command 
+%      setappdata(0,'exportfigdefaults', OPTIONS) 
+%   and for releases after R12 by setting the preference with the
+%   command 
+%      setpref('exportfig', 'defaults', OPTIONS) 
+%
+%   EXPORTFIG(...,PARAM1,VAL1,PARAM2,VAL2,...) specifies
+%   parameters that control various characteristics of the output
+%   file. Any parameter value can be the string 'auto' which means
+%   the parameter uses the default factory behavior, overriding
+%   any other default for the parameter.
+%
+%   Format Paramter:
+%     'Format'  a string
+%          specifies the output format. Defaults to 'eps'. For a
+%          list of export formats type 'help print'.
+%     'Preview' one of the strings 'none', 'tiff'
+%          specifies a preview for EPS files. Defaults to 'none'.
+%
+%   Size Parameters:
+%     'Width'   a positive scalar
+%          specifies the width in the figure's PaperUnits
+%     'Height'  a positive scalar
+%          specifies the height in the figure's PaperUnits
+%     'Bounds' one of the strings 'tight', 'loose'
+%          specifies a tight or loose bounding box. Defaults to 'tight'.
+%     'Reference' an axes handle or a string
+%          specifies that the width and height parameters
+%          are relative to the given axes. If a string is
+%          specified then it must evaluate to an axes handle.
+%
+%     Specifying only one dimension sets the other dimension
+%     so that the exported aspect ratio is the same as the
+%     figure's or reference axes' current aspect ratio. 
+%     If neither dimension is specified the size defaults to 
+%     the width and height from the figure's or reference
+%     axes' size. Tight bounding boxes are only computed for
+%     2-D views and in that case the computed bounds enclose all
+%     text objects.
+%           
+%   Rendering Parameters:
+%     'Color'     one of the strings 'bw', 'gray', 'cmyk'
+%         'bw'    specifies that lines and text are exported in
+%                 black and all other objects in grayscale
+%         'gray'  specifies that all objects are exported in grayscale
+%         'rgb'   specifies that all objects are exported in color
+%                 using the RGB color space
+%         'cmyk'  specifies that all objects are exported in color
+%                 using the CMYK color space
+%     'Renderer'  one of 'painters', 'zbuffer', 'opengl'
+%         specifies the renderer to use
+%     'Resolution'   a positive scalar
+%         specifies the resolution in dots-per-inch.
+%     'LockAxes'  one of 0 or 1
+%         specifies that all axes limits and ticks should be fixed
+%         while exporting.
+%     
+%     The default color setting is 'bw'.
+%
+%   Font Parameters:
+%     'FontMode'     one of the strings 'scaled', 'fixed'
+%     'FontSize'     a positive scalar
+%          in 'scaled' mode multiplies with the font size of each
+%          text object to obtain the exported font size
+%          in 'fixed' mode specifies the font size of all text
+%          objects in points
+%     'DefaultFixedFontSize' a positive scalar
+%          in 'fixed' mode specified the default font size in
+%          points
+%     'FontSizeMin' a positive scalar
+%          specifies the minimum font size allowed after scaling
+%     'FontSizeMax' a positive scalar
+%          specifies the maximum font size allowed after scaling
+%     'FontEncoding' one of the strings 'latin1', 'adobe'
+%          specifies the character encoding of the font
+%     'SeparateText' one of 0 or 1
+%          specifies that the text objects are stored in separate
+%          file as EPS with the base filename having '_t' appended.
+%
+%     If FontMode is 'scaled' but FontSize is not specified then a
+%     scaling factor is computed from the ratio of the size of the
+%     exported figure to the size of the actual figure.
+%
+%     The default 'FontMode' setting is 'scaled'.
+%
+%   Line Width Parameters:
+%     'LineMode'     one of the strings 'scaled', 'fixed'
+%     'LineWidth'    a positive scalar
+%     'DefaultFixedLineWidth' a positive scalar
+%     'LineWidthMin' a positive scalar
+%          specifies the minimum line width allowed after scaling
+%     'LineWidthMax' a positive scalar
+%          specifies the maximum line width allowed after scaling
+%     The semantics of 'Line' parameters are exactly the
+%     same as the corresponding 'Font' parameters, except that
+%     they apply to line widths instead of font sizes.
+%
+%   Style Map Parameter:
+%     'LineStyleMap'    one of [], 'bw', or a function name or handle
+%          specifies how to map line colors to styles. An empty
+%          style map means styles are not changed. The style map
+%          'bw' is a built-in mapping that maps lines with the same
+%          color to the same style and otherwise cycles through the
+%          available styles. A user-specified map is a function
+%          that takes as input a cell array of line objects and
+%          outputs a cell array of line style strings. The default
+%          map is [].
+%      
+%   Examples:
+%     exportfig(gcf,'fig1.eps','height',3);
+%       Exports the current figure to the file named 'fig1.eps' with
+%       a height of 3 inches (assuming the figure's PaperUnits is 
+%       inches) and an aspect ratio the same as the figure's aspect
+%       ratio on screen.
+%
+%     opts = struct('FontMode','fixed','FontSize',10,'height',3);
+%     exportfig(gcf, 'fig2.eps', opts, 'height', 5);
+%       Exports the current figure to 'fig2.eps' with all
+%       text in 10 point fonts and with height 5 inches.
+%
+%   See also PREVIEWFIG, APPLYTOFIG, RESTOREFIG, PRINT.
+
+%  Copyright 2000 Ben Hinkle
+%  Email bug reports and comments to bhinkle@mathworks.com
+
+if (nargin < 2)
+  error('Too few input arguments');
+end
+
+% exportfig(H, filename, [options,] ...)
+H = varargin{1};
+if ~LocalIsHG(H,'figure')
+  error('First argument must be a handle to a figure.');
+end
+filename = varargin{2};
+if ~ischar(filename)
+  error('Second argument must be a string.');
+end
+paramPairs = {varargin{3:end}};
+if nargin > 2
+  if isstruct(paramPairs{1})
+    pcell = LocalToCell(paramPairs{1});
+    paramPairs = {pcell{:}, paramPairs{2:end}};
+  end
+end
+verstr = version;
+majorver = str2num(verstr(1));
+defaults = [];
+if majorver > 5
+  if ispref('exportfig','defaults')
+    defaults = getpref('exportfig','defaults');
+  end
+elseif exist('getappdata')
+  defaults = getappdata(0,'exportfigdefaults');
+end
+if ~isempty(defaults)
+  dcell = LocalToCell(defaults);
+  paramPairs = {dcell{:}, paramPairs{:}};
+end
+
+% Do some validity checking on param-value pairs
+if (rem(length(paramPairs),2) ~= 0)
+  error(['Invalid input syntax. Optional parameters and values' ...
+	 ' must be in pairs.']);
+end
+
+auto.format = 'eps';
+auto.preview = 'none';
+auto.width = -1;
+auto.height = -1;
+auto.color = 'bw';
+auto.defaultfontsize=10;
+auto.fontsize = -1;
+auto.fontmode='scaled';
+auto.fontmin = 8;
+auto.fontmax = 60;
+auto.defaultlinewidth = 1.0;
+auto.linewidth = -1;
+auto.linemode=[];
+auto.linemin = 0.5;
+auto.linemax = 100;
+auto.fontencoding = 'latin1';
+auto.renderer = [];
+auto.resolution = [];
+auto.stylemap = [];
+auto.applystyle = 0;
+auto.refobj = -1;
+auto.bounds = 'tight';
+explicitbounds = 0;
+auto.lockaxes = 1;
+auto.separatetext = 0;
+opts = auto;
+
+% Process param-value pairs
+args = {};
+for k = 1:2:length(paramPairs)
+  param = lower(paramPairs{k});
+  if ~ischar(param)
+    error('Optional parameter names must be strings');
+  end
+  value = paramPairs{k+1};
+  
+  switch (param)
+   case 'format'
+    opts.format = LocalCheckAuto(lower(value),auto.format);
+    if strcmp(opts.format,'preview')
+      error(['Format ''preview'' no longer supported. Use PREVIEWFIG' ...
+	     ' instead.']);
+    end
+   case 'preview'
+    opts.preview = LocalCheckAuto(lower(value),auto.preview);
+    if ~strcmp(opts.preview,{'none','tiff'})
+      error('Preview must be ''none'' or ''tiff''.');
+    end
+   case 'width'
+    opts.width = LocalToNum(value, auto.width);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~LocalIsPositiveScalar(opts.width)
+	error('Width must be a numeric scalar > 0');
+      end
+    end
+   case 'height'
+    opts.height = LocalToNum(value, auto.height);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if(~LocalIsPositiveScalar(opts.height))
+	error('Height must be a numeric scalar > 0');
+      end
+    end
+   case 'color'
+    opts.color = LocalCheckAuto(lower(value),auto.color);
+    if ~strcmp(opts.color,{'bw','gray','rgb','cmyk'})
+      error('Color must be ''bw'', ''gray'',''rgb'' or ''cmyk''.');
+    end
+   case 'fontmode'
+    opts.fontmode = LocalCheckAuto(lower(value),auto.fontmode);
+    if ~strcmp(opts.fontmode,{'scaled','fixed'})
+      error('FontMode must be ''scaled'' or ''fixed''.');
+    end
+   case 'fontsize'
+    opts.fontsize = LocalToNum(value,auto.fontsize);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~LocalIsPositiveScalar(opts.fontsize)
+	error('FontSize must be a numeric scalar > 0');
+      end
+    end
+   case 'defaultfixedfontsize'
+    opts.defaultfontsize = LocalToNum(value,auto.defaultfontsize);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~LocalIsPositiveScalar(opts.defaultfontsize)
+	error('DefaultFixedFontSize must be a numeric scalar > 0');
+      end
+    end
+   case 'fontsizemin'
+    opts.fontmin = LocalToNum(value,auto.fontmin);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~LocalIsPositiveScalar(opts.fontmin)
+	error('FontSizeMin must be a numeric scalar > 0');
+      end
+    end
+   case 'fontsizemax'
+    opts.fontmax = LocalToNum(value,auto.fontmax);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~LocalIsPositiveScalar(opts.fontmax)
+	error('FontSizeMax must be a numeric scalar > 0');
+      end
+    end
+   case 'fontencoding'
+    opts.fontencoding = LocalCheckAuto(lower(value),auto.fontencoding);
+    if ~strcmp(opts.fontencoding,{'latin1','adobe'})
+      error('FontEncoding must be ''latin1'' or ''adobe''.');
+    end
+   case 'linemode'
+    opts.linemode = LocalCheckAuto(lower(value),auto.linemode);
+    if ~strcmp(opts.linemode,{'scaled','fixed'})
+      error('LineMode must be ''scaled'' or ''fixed''.');
+    end
+   case 'linewidth'
+    opts.linewidth = LocalToNum(value,auto.linewidth);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~LocalIsPositiveScalar(opts.linewidth)
+	error('LineWidth must be a numeric scalar > 0');
+      end
+    end
+   case 'defaultfixedlinewidth'
+    opts.defaultlinewidth = LocalToNum(value,auto.defaultlinewidth);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~LocalIsPositiveScalar(opts.defaultlinewidth)
+	error(['DefaultFixedLineWidth must be a numeric scalar >' ...
+	       ' 0']);
+      end
+    end
+   case 'linewidthmin'
+    opts.linemin = LocalToNum(value,auto.linemin);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~LocalIsPositiveScalar(opts.linemin)
+	error('LineWidthMin must be a numeric scalar > 0');
+      end
+    end
+   case 'linewidthmax'
+    opts.linemax = LocalToNum(value,auto.linemax);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~LocalIsPositiveScalar(opts.linemax)
+	error('LineWidthMax must be a numeric scalar > 0');
+      end
+    end
+   case 'linestylemap'
+    opts.stylemap = LocalCheckAuto(value,auto.stylemap);
+   case 'renderer'
+    opts.renderer = LocalCheckAuto(lower(value),auto.renderer);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~strcmp(opts.renderer,{'painters','zbuffer','opengl'})
+	error(['Renderer must be ''painters'', ''zbuffer'' or' ...
+	       ' ''opengl''.']);
+      end
+    end
+   case 'resolution'
+    opts.resolution = LocalToNum(value,auto.resolution);
+    if ~ischar(value) | ~strcmp(value,'auto')
+      if ~(isnumeric(value) & (prod(size(value)) == 1) & (value >= 0));
+	error('Resolution must be a numeric scalar >= 0');
+      end
+    end
+   case 'applystyle' % means to apply the options and not export
+    opts.applystyle = 1;
+   case 'reference'
+    if ischar(value)
+      if strcmp(value,'auto')
+	opts.refobj = auto.refobj;
+      else
+	opts.refobj = eval(value);
+      end
+    else
+      opts.refobj = value;
+    end
+    if ~LocalIsHG(opts.refobj,'axes')
+      error('Reference object must evaluate to an axes handle.');
+    end
+   case 'bounds'
+    opts.bounds = LocalCheckAuto(lower(value),auto.bounds);
+    explicitbounds = 1;
+    if ~strcmp(opts.bounds,{'tight','loose'})
+      error('Bounds must be ''tight'' or ''loose''.');
+    end
+   case 'lockaxes'
+    opts.lockaxes = LocalToNum(value,auto.lockaxes);
+   case 'separatetext'
+    opts.separatetext = LocalToNum(value,auto.separatetext);
+   otherwise
+    error(['Unrecognized option ' param '.']);
+  end
+end
+
+% make sure figure is up-to-date
+drawnow;
+
+allLines  = findall(H, 'type', 'line');
+allText   = findall(H, 'type', 'text');
+allAxes   = findall(H, 'type', 'axes');
+allImages = findall(H, 'type', 'image');
+allLights = findall(H, 'type', 'light');
+allPatch  = findall(H, 'type', 'patch');
+allSurf   = findall(H, 'type', 'surface');
+allRect   = findall(H, 'type', 'rectangle');
+allFont   = [allText; allAxes];
+allColor  = [allLines; allText; allAxes; allLights];
+allMarker = [allLines; allPatch; allSurf];
+allEdge   = [allPatch; allSurf];
+allCData  = [allImages; allPatch; allSurf];
+
+old.objs = {};
+old.prop = {};
+old.values = {};
+
+% Process format
+if strncmp(opts.format,'eps',3) & ~strcmp(opts.preview,'none')
+  args = {args{:}, ['-' opts.preview]};
+end
+
+hadError = 0;
+oldwarn = warning;
+try
+
+  % lock axes limits, ticks and labels if requested
+  if opts.lockaxes
+    old = LocalManualAxesMode(old, allAxes, 'TickMode');
+    old = LocalManualAxesMode(old, allAxes, 'TickLabelMode');
+    old = LocalManualAxesMode(old, allAxes, 'LimMode');
+  end  
+
+  % Process size parameters
+  figurePaperUnits = get(H, 'PaperUnits');
+  oldFigureUnits = get(H, 'Units');
+  oldFigPos = get(H,'Position');
+  set(H, 'Units', figurePaperUnits);
+  figPos = get(H,'Position');
+  refsize = figPos(3:4);
+  if opts.refobj ~= -1
+    oldUnits = get(opts.refobj, 'Units');
+    set(opts.refobj, 'Units', figurePaperUnits);
+    r = get(opts.refobj, 'Position');
+    refsize = r(3:4);
+    set(opts.refobj, 'Units', oldUnits);
+  end
+  aspectRatio = refsize(1)/refsize(2);
+  if (opts.width == -1) & (opts.height == -1)
+    opts.width = refsize(1);
+    opts.height = refsize(2);
+  elseif (opts.width == -1)
+    opts.width = opts.height * aspectRatio;
+  elseif (opts.height == -1)
+    opts.height = opts.width / aspectRatio;
+  end
+  wscale = opts.width/refsize(1);
+  hscale = opts.height/refsize(2);
+  sizescale = min(wscale,hscale);
+  old = LocalPushOldData(old,H,'PaperPositionMode', ...
+			 get(H,'PaperPositionMode'));
+  set(H, 'PaperPositionMode', 'auto');
+  newPos = [figPos(1) figPos(2)+figPos(4)*(1-hscale) ...
+	    wscale*figPos(3) hscale*figPos(4)];
+  set(H, 'Position', newPos);
+  set(H, 'Units', oldFigureUnits);
+  
+  % process line-style map
+  if ~isempty(opts.stylemap) & ~isempty(allLines)
+    oldlstyle = LocalGetAsCell(allLines,'LineStyle');
+    old = LocalPushOldData(old, allLines, {'LineStyle'}, ...
+			   oldlstyle);
+    newlstyle = oldlstyle;
+    if ischar(opts.stylemap) & strcmpi(opts.stylemap,'bw')
+      newlstyle = LocalMapColorToStyle(allLines);
+    else
+      try
+	newlstyle = feval(opts.stylemap,allLines);
+      catch
+	warning(['Skipping stylemap. ' lasterr]);
+      end
+    end
+    set(allLines,{'LineStyle'},newlstyle);
+  end
+
+  % Process rendering parameters
+  switch (opts.color)
+   case {'bw', 'gray'}
+    if ~strcmp(opts.color,'bw') & strncmp(opts.format,'eps',3)
+      opts.format = [opts.format 'c'];
+    end
+    args = {args{:}, ['-d' opts.format]};
+    
+    %compute and set gray colormap
+    oldcmap = get(H,'Colormap');
+    newgrays = 0.30*oldcmap(:,1) + 0.59*oldcmap(:,2) + 0.11*oldcmap(:,3);
+    newcmap = [newgrays newgrays newgrays];
+    old = LocalPushOldData(old, H, 'Colormap', oldcmap);
+    set(H, 'Colormap', newcmap);
+
+    %compute and set ColorSpec and CData properties
+    old = LocalUpdateColors(allColor, 'color', old);
+    old = LocalUpdateColors(allAxes, 'xcolor', old);
+    old = LocalUpdateColors(allAxes, 'ycolor', old);
+    old = LocalUpdateColors(allAxes, 'zcolor', old);
+    old = LocalUpdateColors(allMarker, 'MarkerEdgeColor', old);
+    old = LocalUpdateColors(allMarker, 'MarkerFaceColor', old);
+    old = LocalUpdateColors(allEdge, 'EdgeColor', old);
+    old = LocalUpdateColors(allEdge, 'FaceColor', old);
+    old = LocalUpdateColors(allCData, 'CData', old);
+    
+   case {'rgb','cmyk'}
+    if strncmp(opts.format,'eps',3)
+      opts.format = [opts.format 'c'];
+      args = {args{:}, ['-d' opts.format]};
+      if strcmp(opts.color,'cmyk')
+	args = {args{:}, '-cmyk'};
+      end
+    else
+      args = {args{:}, ['-d' opts.format]};
+    end
+   otherwise
+    error('Invalid Color parameter');
+  end
+  if (~isempty(opts.renderer))
+    args = {args{:}, ['-' opts.renderer]};
+  end
+  if (~isempty(opts.resolution)) | ~strncmp(opts.format,'eps',3)
+    if isempty(opts.resolution)
+      opts.resolution = 0;
+    end
+    args = {args{:}, ['-r' int2str(opts.resolution)]};
+  end
+
+  % Process font parameters
+  if ~isempty(opts.fontmode)
+    oldfonts = LocalGetAsCell(allFont,'FontSize');
+    oldfontunits = LocalGetAsCell(allFont,'FontUnits');
+    set(allFont,'FontUnits','points');
+    switch (opts.fontmode)
+     case 'fixed'
+      if (opts.fontsize == -1)
+	set(allFont,'FontSize',opts.defaultfontsize);
+      else
+	set(allFont,'FontSize',opts.fontsize);
+      end
+     case 'scaled'
+      if (opts.fontsize == -1)
+	scale = sizescale;
+      else
+	scale = opts.fontsize;
+      end
+      newfonts = LocalScale(oldfonts,scale,opts.fontmin,opts.fontmax);
+      set(allFont,{'FontSize'},newfonts);
+     otherwise
+      error('Invalid FontMode parameter');
+    end
+    old = LocalPushOldData(old, allFont, {'FontSize'}, oldfonts);
+    old = LocalPushOldData(old, allFont, {'FontUnits'}, oldfontunits);
+  end
+  if strcmp(opts.fontencoding,'adobe') & strncmp(opts.format,'eps',3)
+    args = {args{:}, '-adobecset'};
+  end
+
+  % Process line parameters
+  if ~isempty(opts.linemode)
+    oldlines = LocalGetAsCell(allMarker,'LineWidth');
+    old = LocalPushOldData(old, allMarker, {'LineWidth'}, oldlines);
+    switch (opts.linemode)
+     case 'fixed'
+      if (opts.linewidth == -1)
+	set(allMarker,'LineWidth',opts.defaultlinewidth);
+      else
+	set(allMarker,'LineWidth',opts.linewidth);
+      end
+     case 'scaled'
+      if (opts.linewidth == -1)
+	scale = sizescale;
+      else
+	scale = opts.linewidth;
+      end
+      newlines = LocalScale(oldlines, scale, opts.linemin, opts.linemax);
+      set(allMarker,{'LineWidth'},newlines);
+    end
+  end
+
+  % adjust figure bounds to surround axes
+  if strcmp(opts.bounds,'tight')
+    if (~strncmp(opts.format,'eps',3) & LocalHas3DPlot(allAxes)) | ...
+	  (strncmp(opts.format,'eps',3) & opts.separatetext)
+      if (explicitbounds == 1)
+	warning(['Cannot compute ''tight'' bounds. Using ''loose''' ...
+		 ' bounds.']);
+      end
+      opts.bounds = 'loose';
+    end
+  end
+  warning('off');
+  if ~isempty(allAxes)
+    if strncmp(opts.format,'eps',3)
+      if strcmp(opts.bounds,'loose')
+	args = {args{:}, '-loose'};
+      end
+      old = LocalPushOldData(old,H,'Position', oldFigPos);
+    elseif strcmp(opts.bounds,'tight')
+      oldaunits = LocalGetAsCell(allAxes,'Units');
+      oldapos = LocalGetAsCell(allAxes,'Position');
+      oldtunits = LocalGetAsCell(allText,'units');
+      oldtpos = LocalGetAsCell(allText,'Position');
+      set(allAxes,'units','points');
+      apos = LocalGetAsCell(allAxes,'Position');
+      oldunits = get(H,'Units');
+      set(H,'units','points');
+      origfr = get(H,'position');
+      fr = [];
+      for k=1:length(allAxes)
+	if ~strcmpi(get(allAxes(k),'Tag'),'legend')
+	  axesR = apos{k};
+	  r = LocalAxesTightBoundingBox(axesR, allAxes(k));
+	  r(1:2) = r(1:2) + axesR(1:2);
+	  fr = LocalUnionRect(fr,r);
+	end
+      end
+      if isempty(fr)
+	fr = [0 0 origfr(3:4)];
+      end
+      for k=1:length(allAxes)
+	ax = allAxes(k);
+	r = apos{k};
+	r(1:2) = r(1:2) - fr(1:2);
+	set(ax,'Position',r);
+      end
+      old = LocalPushOldData(old, allAxes, {'Position'}, oldapos);
+      old = LocalPushOldData(old, allText, {'Position'}, oldtpos);
+      old = LocalPushOldData(old, allText, {'Units'}, oldtunits);
+      old = LocalPushOldData(old, allAxes, {'Units'}, oldaunits);
+      old = LocalPushOldData(old, H, 'Position', oldFigPos);
+      old = LocalPushOldData(old, H, 'Units', oldFigureUnits);
+      r = [origfr(1) origfr(2)+origfr(4)-fr(4) fr(3:4)];
+      set(H,'Position',r);
+    else
+      args = {args{:}, '-loose'};
+      old = LocalPushOldData(old,H,'Position', oldFigPos);
+    end
+  end
+  
+  % Process text in a separate file if needed
+  if opts.separatetext & ~opts.applystyle
+    % First hide all text and export
+    oldtvis = LocalGetAsCell(allText,'visible');
+    set(allText,'visible','off');
+    oldax = LocalGetAsCell(allAxes,'XTickLabel',1);
+    olday = LocalGetAsCell(allAxes,'YTickLabel',1);
+    oldaz = LocalGetAsCell(allAxes,'ZTickLabel',1);
+    null = cell(length(oldax),1);
+    [null{:}] = deal([]);
+    set(allAxes,{'XTickLabel'},null);
+    set(allAxes,{'YTickLabel'},null);
+    set(allAxes,{'ZTickLabel'},null);
+    print(H, filename, args{:});
+    set(allText,{'Visible'},oldtvis);
+    set(allAxes,{'XTickLabel'},oldax);
+    set(allAxes,{'YTickLabel'},olday);
+    set(allAxes,{'ZTickLabel'},oldaz);
+    % Now hide all non-text and export as eps in painters
+    [path, name, ext] = fileparts(filename);
+    tfile = fullfile(path,[name '_t.eps']);
+    tfile2 = fullfile(path,[name '_t2.eps']);
+    foundRenderer = 0;
+    for k=1:length(args)
+      if strncmp('-d',args{k},2)
+	args{k} = '-deps';
+      elseif strncmp('-zbuffer',args{k},8) | ...
+	    strncmp('-opengl', args{k},6)
+	args{k} = '-painters';
+	foundRenderer = 1;
+      end
+    end
+    if ~foundRenderer
+      args = {args{:}, '-painters'};
+    end
+    allNonText = [allLines; allLights; allPatch; ...
+		  allImages; allSurf; allRect];
+    oldvis = LocalGetAsCell(allNonText,'visible');
+    oldc = LocalGetAsCell(allAxes,'color');
+    oldaxg = LocalGetAsCell(allAxes,'XGrid');
+    oldayg = LocalGetAsCell(allAxes,'YGrid');
+    oldazg = LocalGetAsCell(allAxes,'ZGrid');
+    [null{:}] = deal('off');
+    set(allAxes,{'XGrid'},null);
+    set(allAxes,{'YGrid'},null);
+    set(allAxes,{'ZGrid'},null);
+    set(allNonText,'Visible','off');
+    set(allAxes,'Color','none');
+    print(H, tfile2, args{:});
+    set(allNonText,{'Visible'},oldvis);
+    set(allAxes,{'Color'},oldc);
+    set(allAxes,{'XGrid'},oldaxg);
+    set(allAxes,{'YGrid'},oldayg);
+    set(allAxes,{'ZGrid'},oldazg);
+    %hack up the postscript file
+    fid1 = fopen(tfile,'w');
+    fid2 = fopen(tfile2,'r');
+    line = fgetl(fid2);
+    while ischar(line)
+      if strncmp(line,'%%Title',7)
+	fprintf(fid1,'%s\n',['%%Title: ', tfile]);
+      elseif (length(line) < 3) 
+	fprintf(fid1,'%s\n',line);
+      elseif ~strcmp(line(end-2:end),' PR') & ...
+	    ~strcmp(line(end-1:end),' L')
+	fprintf(fid1,'%s\n',line);
+      end
+      line = fgetl(fid2);
+    end
+    fclose(fid1);
+    fclose(fid2);
+    delete(tfile2);
+    
+  elseif ~opts.applystyle
+    drawnow;
+    print(H, filename, args{:});
+  end
+  warning(oldwarn);
+  
+catch
+  warning(oldwarn);
+  hadError = 1;
+end
+
+% Restore figure settings
+if opts.applystyle
+  varargout{1} = old;
+else
+  for n=1:length(old.objs)
+    if ~iscell(old.values{n}) & iscell(old.prop{n})
+      old.values{n} = {old.values{n}};
+    end
+    set(old.objs{n}, old.prop{n}, old.values{n});
+  end
+end
+
+if hadError
+  error(deblank(lasterr));
+end
+
+%
+%  Local Functions
+%
+
+function outData = LocalPushOldData(inData, objs, prop, values)
+outData.objs = {objs, inData.objs{:}};
+outData.prop = {prop, inData.prop{:}};
+outData.values = {values, inData.values{:}};
+
+function cellArray = LocalGetAsCell(fig,prop,allowemptycell);
+cellArray = get(fig,prop);
+if nargin < 3
+  allowemptycell = 0;
+end
+if ~iscell(cellArray) & (allowemptycell | ~isempty(cellArray))
+  cellArray = {cellArray};
+end
+
+function newArray = LocalScale(inArray, scale, minv, maxv)
+n = length(inArray);
+newArray = cell(n,1);
+for k=1:n
+  newArray{k} = min(maxv,max(minv,scale*inArray{k}(1)));
+end
+
+function gray = LocalMapToGray1(color)
+gray = color;
+if ischar(color)
+  switch color(1)
+   case 'y'
+    color = [1 1 0];
+   case 'm'
+    color = [1 0 1];
+   case 'c'
+    color = [0 1 1];
+   case 'r'
+    color = [1 0 0];
+   case 'g'
+    color = [0 1 0];
+   case 'b'
+    color = [0 0 1];
+   case 'w'
+    color = [1 1 1];
+   case 'k'
+    color = [0 0 0];
+  end
+end
+if ~ischar(color)
+  gray = 0.30*color(1) + 0.59*color(2) + 0.11*color(3);
+end
+
+function newArray = LocalMapToGray(inArray);
+n = length(inArray);
+newArray = cell(n,1);
+for k=1:n
+  color = inArray{k};
+  if ~isempty(color)
+    color = LocalMapToGray1(color);
+  end
+  if isempty(color) | ischar(color)
+    newArray{k} = color;
+  else
+    newArray{k} = [color color color];
+  end
+end
+
+function newArray = LocalMapColorToStyle(inArray);
+inArray = LocalGetAsCell(inArray,'Color');
+n = length(inArray);
+newArray = cell(n,1);
+styles = {'-','--',':','-.'};
+uniques = [];
+nstyles = length(styles);
+for k=1:n
+  gray = LocalMapToGray1(inArray{k});
+  if isempty(gray) | ischar(gray) | gray < .05
+    newArray{k} = '-';
+  else
+    if ~isempty(uniques) & any(gray == uniques)
+      ind = find(gray==uniques);
+    else
+      uniques = [uniques gray];
+      ind = length(uniques);
+    end
+    newArray{k} = styles{mod(ind-1,nstyles)+1};
+  end
+end
+
+function newArray = LocalMapCData(inArray);
+n = length(inArray);
+newArray = cell(n,1);
+for k=1:n
+  color = inArray{k};
+  if (ndims(color) == 3) & isa(color,'double')
+    gray = 0.30*color(:,:,1) + 0.59*color(:,:,2) + 0.11*color(:,:,3);
+    color(:,:,1) = gray;
+    color(:,:,2) = gray;
+    color(:,:,3) = gray;
+  end
+  newArray{k} = color;
+end
+
+function outData = LocalUpdateColors(inArray, prop, inData)
+value = LocalGetAsCell(inArray,prop);
+outData.objs = {inData.objs{:}, inArray};
+outData.prop = {inData.prop{:}, {prop}};
+outData.values = {inData.values{:}, value};
+if (~isempty(value))
+  if strcmp(prop,'CData') 
+    value = LocalMapCData(value);
+  else
+    value = LocalMapToGray(value);
+  end
+  set(inArray,{prop},value);
+end
+
+function bool = LocalIsPositiveScalar(value)
+bool = isnumeric(value) & ...
+       prod(size(value)) == 1 & ...
+       value > 0;
+
+function value = LocalToNum(value,auto)
+if ischar(value)
+  if strcmp(value,'auto')
+    value = auto;
+  else
+    value = str2num(value);
+  end
+end
+
+%convert a struct to {field1,val1,field2,val2,...}
+function c = LocalToCell(s)
+f = fieldnames(s);
+v = struct2cell(s);
+opts = cell(2,length(f));
+opts(1,:) = f;
+opts(2,:) = v;
+c = {opts{:}};
+
+function c = LocalIsHG(obj,hgtype)
+c = 0;
+if (length(obj) == 1) & ishandle(obj) 
+  c = strcmp(get(obj,'type'),hgtype);
+end
+
+function c = LocalHas3DPlot(a)
+zticks = LocalGetAsCell(a,'ZTickLabel');
+c = 0;
+for k=1:length(zticks)
+  if ~isempty(zticks{k})
+    c = 1;
+    return;
+  end
+end
+
+function r = LocalUnionRect(r1,r2)
+if isempty(r1)
+  r = r2;
+elseif isempty(r2)
+  r = r1;
+elseif max(r2(3:4)) > 0
+  left = min(r1(1),r2(1));
+  bot = min(r1(2),r2(2));
+  right = max(r1(1)+r1(3),r2(1)+r2(3));
+  top = max(r1(2)+r1(4),r2(2)+r2(4));
+  r = [left bot right-left top-bot];
+else
+  r = r1;
+end
+
+function c = LocalLabelsMatchTicks(labs,ticks)
+c = 0;
+try
+  t1 = num2str(ticks(1));
+  n = length(ticks);
+  tend = num2str(ticks(n));
+  c = strncmp(labs(1),t1,length(labs(1))) & ...
+      strncmp(labs(n),tend,length(labs(n)));
+end
+
+function r = LocalAxesTightBoundingBox(axesR, a)
+r = [];
+atext = findall(a,'type','text','visible','on');
+if ~isempty(atext)
+  set(atext,'units','points');
+  res=LocalGetAsCell(atext,'extent');
+  for n=1:length(atext)
+    r = LocalUnionRect(r,res{n});
+  end
+end
+if strcmp(get(a,'visible'),'on')
+  r = LocalUnionRect(r,[0 0 axesR(3:4)]);
+  oldunits = get(a,'fontunits');
+  set(a,'fontunits','points');
+  label = text(0,0,'','parent',a,...
+	       'units','points',...
+	       'fontsize',get(a,'fontsize'),...
+	       'fontname',get(a,'fontname'),...
+	       'fontweight',get(a,'fontweight'),...
+	       'fontangle',get(a,'fontangle'),...
+	       'visible','off');
+  fs = get(a,'fontsize');
+
+  % handle y axis tick labels
+  ry = [0 -fs/2 0 axesR(4)+fs];
+  ylabs = get(a,'yticklabels');
+  yticks = get(a,'ytick');
+  maxw = 0;
+  if ~isempty(ylabs)
+    for n=1:size(ylabs,1)
+      set(label,'string',ylabs(n,:));
+      ext = get(label,'extent');
+      maxw = max(maxw,ext(3));
+    end
+    if ~LocalLabelsMatchTicks(ylabs,yticks) & ...
+	  strcmp(get(a,'xaxislocation'),'bottom')
+      ry(4) = ry(4) + 1.5*ext(4);
+    end
+    if strcmp(get(a,'yaxislocation'),'left')
+      ry(1) = -(maxw+5);
+    else
+      ry(1) = axesR(3);
+    end
+    ry(3) = maxw+5;
+    r = LocalUnionRect(r,ry);
+  end
+
+  % handle x axis tick labels
+  rx = [0 0 0 fs+5];
+  xlabs = get(a,'xticklabels');
+  xticks = get(a,'xtick');
+  if ~isempty(xlabs)
+    if strcmp(get(a,'xaxislocation'),'bottom')
+      rx(2) = -(fs+5);
+      if ~LocalLabelsMatchTicks(xlabs,xticks);
+	rx(4) = rx(4) + 2*fs;
+	rx(2) = rx(2) - 2*fs;
+      end
+    else
+      rx(2) = axesR(4);
+      % exponent is still below axes
+      if ~LocalLabelsMatchTicks(xlabs,xticks);
+	rx(4) = rx(4) + axesR(4) + 2*fs;
+	rx(2) = -2*fs;
+      end
+    end
+    set(label,'string',xlabs(1,:));
+    ext1 = get(label,'extent');
+    rx(1) = -ext1(3)/2;
+    set(label,'string',xlabs(size(xlabs,1),:));
+    ext2 = get(label,'extent');
+    rx(3) = axesR(3) + (ext2(3) + ext1(3))/2;
+    r = LocalUnionRect(r,rx);
+  end
+  set(a,'fontunits',oldunits);
+  delete(label);
+end
+
+function c = LocalManualAxesMode(old, allAxes, base)
+xs = ['X' base];
+ys = ['Y' base];
+zs = ['Z' base];
+oldXMode = LocalGetAsCell(allAxes,xs);
+oldYMode = LocalGetAsCell(allAxes,ys);
+oldZMode = LocalGetAsCell(allAxes,zs);
+old = LocalPushOldData(old, allAxes, {xs}, oldXMode);
+old = LocalPushOldData(old, allAxes, {ys}, oldYMode);
+old = LocalPushOldData(old, allAxes, {zs}, oldZMode);
+set(allAxes,xs,'manual');
+set(allAxes,ys,'manual');
+set(allAxes,zs,'manual');
+c = old;
+
+function val = LocalCheckAuto(val, auto)
+if ischar(val) & strcmp(val,'auto')
+  val = auto;
+end
diff --git a/sourcecodes/bnt-master/KPMtools/extend_domain_table.m b/sourcecodes/bnt-master/KPMtools/extend_domain_table.m
new file mode 100644
index 00000000..4ed0b2cd
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/extend_domain_table.m
@@ -0,0 +1,24 @@
+function B = extend_domain_table(A, smalldom, smallsz, bigdom, bigsz)
+% EXTEND_DOMAIN_TABLE Expand an array so it has the desired size.
+% B = extend_domain_table(A, smalldom, smallsz, bigdom, bigsz)
+%
+% A is the array with domain smalldom and sizes smallsz.
+% bigdom is the desired domain, with sizes bigsz.
+%
+% Example:
+% smalldom = [1 3], smallsz = [2 4], bigdom = [1 2 3 4], bigsz = [2 1 4 5],
+% so B(i,j,k,l) = A(i,k) for i in 1:2, j in 1:1, k in 1:4, l in 1:5
+
+if isequal(size(A), [1 1]) % a scalar
+  B = A; % * myones(bigsz);
+  return;
+end
+
+map = find_equiv_posns(smalldom, bigdom);
+sz = ones(1, length(bigdom));
+sz(map) = smallsz;
+B = myreshape(A, sz); % add dimensions for the stuff not in A
+sz = bigsz;
+sz(map) = 1; % don't replicate along A's dimensions
+B = myrepmat(B, sz(:)');
+                           
diff --git a/sourcecodes/bnt-master/KPMtools/factorial.m b/sourcecodes/bnt-master/KPMtools/factorial.m
new file mode 100644
index 00000000..7eab9a5f
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/factorial.m
@@ -0,0 +1,9 @@
+function x = factorial(n)
+% FACTORIAL Compute n!
+% x = factorial(n)
+
+if n == 0
+  x = 1;
+else
+  x = n*factorial(n-1);
+end    
diff --git a/sourcecodes/bnt-master/KPMtools/filepartsLast.m b/sourcecodes/bnt-master/KPMtools/filepartsLast.m
new file mode 100644
index 00000000..58c5511a
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/filepartsLast.m
@@ -0,0 +1,12 @@
+function [last] = filepartsLast(fname)
+% filepartsLast Return the last part of a filename (strip off directory and suffix)
+% function filepartsLast(fname)
+%
+% Examples
+% filepartsLast('C:/foo/bar') = 'bar'
+% filepartsLast('C:/foo/bar.mat') = 'bar'
+% filepartsLast('C:/foo/bar.mat.gz') = 'bar.mat'
+% filepartsLast('bar.mat') = 'bar'
+
+[pathstr,name,ext,versn] = fileparts(fname);
+last = name;
diff --git a/sourcecodes/bnt-master/KPMtools/find_equiv_posns.m b/sourcecodes/bnt-master/KPMtools/find_equiv_posns.m
new file mode 100644
index 00000000..cc2b8b1b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/find_equiv_posns.m
@@ -0,0 +1,24 @@
+function p = find_equiv_posns(vsmall, vlarge)
+% FIND_EQUIV_POSNS p[i] = the place where vsmall[i] occurs in vlarge.
+% p = find_equiv_posns(vsmall, vlarge)
+% THE VECTORS ARE ASSUMED TO BE SORTED.
+%
+% e.g., vsmall=[2,8], vlarge=[2,7,8,4], p=[1,3]
+%
+% In R/S, this function is called 'match'
+ 
+%if ~mysubset(vsmall, vlarge)
+%  error('small domain must occur in large domain');
+%end
+
+if isempty(vsmall) || isempty(vlarge)
+  p = [];
+  return;
+end
+  
+bitvec = sparse(1, max(vlarge)); 
+%bitvec = zeros(1, max(vlarge));
+bitvec(vsmall) = 1;
+p = find(bitvec(vlarge));
+
+%p = find(ismember(vlarge, vsmall)); % slower
diff --git a/sourcecodes/bnt-master/KPMtools/fullfileKPM.m b/sourcecodes/bnt-master/KPMtools/fullfileKPM.m
new file mode 100644
index 00000000..a3ab4432
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/fullfileKPM.m
@@ -0,0 +1,6 @@
+function f = fullfileKPM(varargin)
+% fullfileKPM Concatenate strings with file separator, then convert it to a/b/c
+% function f = fullfileKPM(varargin)
+
+f = fullfile(varargin{:});
+f = strrep(f, '\', '/');
diff --git a/sourcecodes/bnt-master/KPMtools/genpathKPM.m b/sourcecodes/bnt-master/KPMtools/genpathKPM.m
new file mode 100644
index 00000000..8994fc9b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/genpathKPM.m
@@ -0,0 +1,45 @@
+function p = genpathKPM(d)
+% genpathKPM Like built-in genpath, but omits directories whose name is 'Old', 'old' or 'CVS'
+% function p = genpathKPM(d)
+
+if nargin==0,
+  p = genpath(fullfile(matlabroot,'toolbox'));
+  if length(p) > 1, p(end) = []; end % Remove trailing pathsep
+  return
+end
+
+% initialise variables
+methodsep = '@';  % qualifier for overloaded method directories
+p = '';           % path to be returned
+
+% Generate path based on given root directory
+files = dir(d);
+if isempty(files)
+  return
+end
+
+% Add d to the path even if it is empty.
+p = [p d pathsep];
+
+% set logical vector for subdirectory entries in d
+isdir = logical(cat(1,files.isdir));
+%
+% Recursively descend through directories which are neither
+% private nor "class" directories.
+%
+dirs = files(isdir); % select only directory entries from the current listing
+
+for i=1:length(dirs)
+   dirname = dirs(i).name;
+   if    ~strcmp( dirname,'.')         & ...
+         ~strcmp( dirname,'..')        & ...
+         ~strncmp( dirname,methodsep,1)& ...
+         ~strcmp( dirname,'private') & ...
+	 ~strcmp( dirname, 'old') & ...      % KPM
+	 ~strcmp( dirname, 'Old') & ... % KPM
+     	 ~strcmp( dirname, 'CVS')            % KPM
+      p = [p genpathKPM(fullfile(d,dirname))]; % recursive calling of this function.
+   end
+end
+
+%------------------------------------------------------------------------------
diff --git a/sourcecodes/bnt-master/KPMtools/hash_add.m b/sourcecodes/bnt-master/KPMtools/hash_add.m
new file mode 100644
index 00000000..f302d8f1
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/hash_add.m
@@ -0,0 +1,19 @@
+function hash_add(key, val, fname)
+% HASH_ADD Append key,value pair to end of hashtable stored in a file
+% function hash_add(key, val, filename)
+%
+% See hash_lookup for an example
+
+if ~exist(fname, 'file')
+  % new hashtable
+  hashtable.key{1} = key;
+  hashtable.value{1} = val;
+else
+  %hashtable = importdata(fname);
+  %hashtable = load(fname, '-mat');
+  load(fname, '-mat');
+  Nentries = length(hashtable.key);
+  hashtable.key{Nentries+1} = key;
+  hashtable.value{Nentries+1} = val;
+end
+save(fname, 'hashtable', '-mat');
diff --git a/sourcecodes/bnt-master/KPMtools/hash_del.m b/sourcecodes/bnt-master/KPMtools/hash_del.m
new file mode 100644
index 00000000..c5de3daa
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/hash_del.m
@@ -0,0 +1,26 @@
+function ndx = hash_del(key, fname)
+% HASH_DEL Remove all entries that match key  from hashtable stored in a file
+% ndx = hash_del(key, fname)
+%
+% Returns indices of matching entries (if any)
+% See hash_lookup for an example
+
+ndx = [];
+
+if ~exist(fname, 'file')
+  % new hashtable - no op
+else
+  %hashtable = importdata(fname);
+  %hashtable = load(fname, '-mat');
+  load(fname, '-mat');
+  Nentries = length(hashtable.key);
+  for i=1:Nentries
+    if isequal(hashtable.key{i}, key)
+      ndx = [ndx i];
+    end
+  end
+  hashtable.key(ndx) = [];
+  hashtable.value(ndx) = [];
+  save(fname, 'hashtable', '-mat');
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/hash_lookup.m b/sourcecodes/bnt-master/KPMtools/hash_lookup.m
new file mode 100644
index 00000000..847c6d58
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/hash_lookup.m
@@ -0,0 +1,34 @@
+function [val, found, Nentries] = hash_lookup(key, fname)
+% HASH_LOOKUP Lookup a key in a hash table stored in a file using linear search
+% function [val, found, Nentries] = hash_lookup(key, filename)
+%
+% Example:
+% If htbl.mat does not exist,
+%   [val,found,N] = hash_lookup('foo', 'htbl')
+% returns found val = [], found = 0, N = 0
+%   hash_add('foo', 42, 'htbl')
+%   hash_add('bar', [1:10], 'htbl')
+%   [val,found,N] = hash_lookup('foo', 'htbl')
+% now returns val = 42, found = 1, N = 2
+%
+% Type 'delete htbl' to delete the file/ reset the hashtable
+
+
+val = [];
+found = 0;
+
+if exist(fname, 'file')==0
+  % new hashtable
+  Nentries = 0;
+else
+  %hashtable = importdata(fname);
+  load(fname);
+  Nentries = length(hashtable.key);
+  for i=1:Nentries
+    if isequal(hashtable.key{i}, key)
+      val = hashtable.value{i};
+      found = 1;
+      break;
+    end
+  end
+end
diff --git a/sourcecodes/bnt-master/KPMtools/hsvKPM.m b/sourcecodes/bnt-master/KPMtools/hsvKPM.m
new file mode 100644
index 00000000..29521ae5
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/hsvKPM.m
@@ -0,0 +1,7 @@
+function colors = hsvKPM(N)
+% hsvKPM Like built-in HSV, except it randomizes the order, so that adjacent colors are dis-similar
+% function colors = hsvKPM(N)
+
+colors = hsv(N);
+perm = randperm(N);
+colors = colors(perm,:);
diff --git a/sourcecodes/bnt-master/KPMtools/hungarian.m b/sourcecodes/bnt-master/KPMtools/hungarian.m
new file mode 100644
index 00000000..0b493f07
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/hungarian.m
@@ -0,0 +1,464 @@
+function [C,T]=hungarian(A)
+%HUNGARIAN Solve the Assignment problem using the Hungarian method.
+%
+%[C,T]=hungarian(A)
+%A - a square cost matrix.
+%C - the optimal assignment.
+%T - the cost of the optimal assignment.
+
+% Adapted from the FORTRAN IV code in Carpaneto and Toth, "Algorithm 548:
+% Solution of the assignment problem [H]", ACM Transactions on
+% Mathematical Software, 6(1):104-111, 1980.
+
+% v1.0  96-06-14. Niclas Borlin, niclas@cs.umu.se.
+%                 Department of Computing Science, Umeå University,
+%                 Sweden. 
+%                 All standard disclaimers apply.
+
+% A substantial effort was put into this code. If you use it for a
+% publication or otherwise, please include an acknowledgement or at least
+% notify me by email. /Niclas
+
+[m,n]=size(A);
+
+if (m~=n)
+    error('HUNGARIAN: Cost matrix must be square!');
+end
+
+% Save original cost matrix.
+orig=A;
+
+% Reduce matrix.
+A=hminired(A);
+
+% Do an initial assignment.
+[A,C,U]=hminiass(A);
+
+% Repeat while we have unassigned rows.
+while (U(n+1))
+    % Start with no path, no unchecked zeros, and no unexplored rows.
+    LR=zeros(1,n);
+    LC=zeros(1,n);
+    CH=zeros(1,n);
+    RH=[zeros(1,n) -1];
+    
+    % No labelled columns.
+    SLC=[];
+    
+    % Start path in first unassigned row.
+    r=U(n+1);
+    % Mark row with end-of-path label.
+    LR(r)=-1;
+    % Insert row first in labelled row set.
+    SLR=r;
+    
+    % Repeat until we manage to find an assignable zero.
+    while (1)
+        % If there are free zeros in row r
+        if (A(r,n+1)~=0)
+            % ...get column of first free zero.
+            l=-A(r,n+1);
+            
+            % If there are more free zeros in row r and row r in not
+            % yet marked as unexplored..
+            if (A(r,l)~=0 & RH(r)==0)
+                % Insert row r first in unexplored list.
+                RH(r)=RH(n+1);
+                RH(n+1)=r;
+                
+                % Mark in which column the next unexplored zero in this row
+                % is.
+                CH(r)=-A(r,l);
+            end
+        else
+            % If all rows are explored..
+            if (RH(n+1)<=0)
+                % Reduce matrix.
+                [A,CH,RH]=hmreduce(A,CH,RH,LC,LR,SLC,SLR);
+            end
+            
+            % Re-start with first unexplored row.
+            r=RH(n+1);
+            % Get column of next free zero in row r.
+            l=CH(r);
+            % Advance "column of next free zero".
+            CH(r)=-A(r,l);
+            % If this zero is last in the list..
+            if (A(r,l)==0)
+                % ...remove row r from unexplored list.
+                RH(n+1)=RH(r);
+                RH(r)=0;
+            end
+        end
+        
+        % While the column l is labelled, i.e. in path.
+        while (LC(l)~=0)
+            % If row r is explored..
+            if (RH(r)==0)
+                % If all rows are explored..
+                if (RH(n+1)<=0)
+                    % Reduce cost matrix.
+                    [A,CH,RH]=hmreduce(A,CH,RH,LC,LR,SLC,SLR);
+                end
+                
+                % Re-start with first unexplored row.
+                r=RH(n+1);
+            end
+            
+            % Get column of next free zero in row r.
+            l=CH(r);
+            
+            % Advance "column of next free zero".
+            CH(r)=-A(r,l);
+            
+            % If this zero is last in list..
+            if(A(r,l)==0)
+                % ...remove row r from unexplored list.
+                RH(n+1)=RH(r);
+                RH(r)=0;
+            end
+        end
+        
+        % If the column found is unassigned..
+        if (C(l)==0)
+            % Flip all zeros along the path in LR,LC.
+            [A,C,U]=hmflip(A,C,LC,LR,U,l,r);
+            % ...and exit to continue with next unassigned row.
+            break;
+        else
+            % ...else add zero to path.
+            
+            % Label column l with row r.
+            LC(l)=r;
+            
+            % Add l to the set of labelled columns.
+            SLC=[SLC l];
+            
+            % Continue with the row assigned to column l.
+            r=C(l);
+            
+            % Label row r with column l.
+            LR(r)=l;
+            
+            % Add r to the set of labelled rows.
+            SLR=[SLR r];
+        end
+    end
+end
+
+% Calculate the total cost.
+T=sum(orig(logical(sparse(C,1:size(orig,2),1))));
+
+
+function A=hminired(A)
+%HMINIRED Initial reduction of cost matrix for the Hungarian method.
+%
+%B=assredin(A)
+%A - the unreduced cost matris.
+%B - the reduced cost matrix with linked zeros in each row.
+
+% v1.0  96-06-13. Niclas Borlin, niclas@cs.umu.se.
+
+[m,n]=size(A);
+
+% Subtract column-minimum values from each column.
+colMin=min(A);
+A=A-colMin(ones(n,1),:);
+
+% Subtract row-minimum values from each row.
+rowMin=min(A')';
+A=A-rowMin(:,ones(1,n));
+
+% Get positions of all zeros.
+[i,j]=find(A==0);
+
+% Extend A to give room for row zero list header column.
+A(1,n+1)=0;
+for k=1:n
+    % Get all column in this row. 
+    cols=j(k==i)';
+    % Insert pointers in matrix.
+    A(k,[n+1 cols])=[-cols 0];
+end
+
+
+function [A,C,U]=hminiass(A)
+%HMINIASS Initial assignment of the Hungarian method.
+%
+%[B,C,U]=hminiass(A)
+%A - the reduced cost matrix.
+%B - the reduced cost matrix, with assigned zeros removed from lists.
+%C - a vector. C(J)=I means row I is assigned to column J,
+%              i.e. there is an assigned zero in position I,J.
+%U - a vector with a linked list of unassigned rows.
+
+% v1.0  96-06-14. Niclas Borlin, niclas@cs.umu.se.
+
+[n,np1]=size(A);
+
+% Initalize return vectors.
+C=zeros(1,n);
+U=zeros(1,n+1);
+
+% Initialize last/next zero "pointers".
+LZ=zeros(1,n);
+NZ=zeros(1,n);
+
+for i=1:n
+    % Set j to first unassigned zero in row i.
+	lj=n+1;
+	j=-A(i,lj);
+
+    % Repeat until we have no more zeros (j==0) or we find a zero
+	% in an unassigned column (c(j)==0).
+    
+	while (C(j)~=0)
+		% Advance lj and j in zero list.
+		lj=j;
+		j=-A(i,lj);
+	
+		% Stop if we hit end of list.
+		if (j==0)
+			break;
+		end
+	end
+
+	if (j~=0)
+		% We found a zero in an unassigned column.
+		
+		% Assign row i to column j.
+		C(j)=i;
+		
+		% Remove A(i,j) from unassigned zero list.
+		A(i,lj)=A(i,j);
+
+		% Update next/last unassigned zero pointers.
+		NZ(i)=-A(i,j);
+		LZ(i)=lj;
+
+		% Indicate A(i,j) is an assigned zero.
+		A(i,j)=0;
+	else
+		% We found no zero in an unassigned column.
+
+		% Check all zeros in this row.
+
+		lj=n+1;
+		j=-A(i,lj);
+		
+		% Check all zeros in this row for a suitable zero in another row.
+		while (j~=0)
+			% Check the in the row assigned to this column.
+			r=C(j);
+			
+			% Pick up last/next pointers.
+			lm=LZ(r);
+			m=NZ(r);
+			
+			% Check all unchecked zeros in free list of this row.
+			while (m~=0)
+				% Stop if we find an unassigned column.
+				if (C(m)==0)
+					break;
+				end
+				
+				% Advance one step in list.
+				lm=m;
+				m=-A(r,lm);
+			end
+			
+			if (m==0)
+				% We failed on row r. Continue with next zero on row i.
+				lj=j;
+				j=-A(i,lj);
+			else
+				% We found a zero in an unassigned column.
+			
+				% Replace zero at (r,m) in unassigned list with zero at (r,j)
+				A(r,lm)=-j;
+				A(r,j)=A(r,m);
+			
+				% Update last/next pointers in row r.
+				NZ(r)=-A(r,m);
+				LZ(r)=j;
+			
+				% Mark A(r,m) as an assigned zero in the matrix . . .
+				A(r,m)=0;
+			
+				% ...and in the assignment vector.
+				C(m)=r;
+			
+				% Remove A(i,j) from unassigned list.
+				A(i,lj)=A(i,j);
+			
+				% Update last/next pointers in row r.
+				NZ(i)=-A(i,j);
+				LZ(i)=lj;
+			
+				% Mark A(r,m) as an assigned zero in the matrix . . .
+				A(i,j)=0;
+			
+				% ...and in the assignment vector.
+				C(j)=i;
+				
+				% Stop search.
+				break;
+			end
+		end
+	end
+end
+
+% Create vector with list of unassigned rows.
+
+% Mark all rows have assignment.
+r=zeros(1,n);
+rows=C(C~=0);
+r(rows)=rows;
+empty=find(r==0);
+
+% Create vector with linked list of unassigned rows.
+U=zeros(1,n+1);
+U([n+1 empty])=[empty 0];
+
+
+function [A,C,U]=hmflip(A,C,LC,LR,U,l,r)
+%HMFLIP Flip assignment state of all zeros along a path.
+%
+%[A,C,U]=hmflip(A,C,LC,LR,U,l,r)
+%Input:
+%A   - the cost matrix.
+%C   - the assignment vector.
+%LC  - the column label vector.
+%LR  - the row label vector.
+%U   - the 
+%r,l - position of last zero in path.
+%Output:
+%A   - updated cost matrix.
+%C   - updated assignment vector.
+%U   - updated unassigned row list vector.
+
+% v1.0  96-06-14. Niclas Borlin, niclas@cs.umu.se.
+
+n=size(A,1);
+
+while (1)
+    % Move assignment in column l to row r.
+    C(l)=r;
+    
+    % Find zero to be removed from zero list..
+    
+    % Find zero before this.
+    m=find(A(r,:)==-l);
+    
+    % Link past this zero.
+    A(r,m)=A(r,l);
+    
+    A(r,l)=0;
+    
+    % If this was the first zero of the path..
+    if (LR(r)<0)
+        ...remove row from unassigned row list and return.
+        U(n+1)=U(r);
+        U(r)=0;
+        return;
+    else
+        
+        % Move back in this row along the path and get column of next zero.
+        l=LR(r);
+        
+        % Insert zero at (r,l) first in zero list.
+        A(r,l)=A(r,n+1);
+        A(r,n+1)=-l;
+        
+        % Continue back along the column to get row of next zero in path.
+        r=LC(l);
+    end
+end
+
+
+function [A,CH,RH]=hmreduce(A,CH,RH,LC,LR,SLC,SLR)
+%HMREDUCE Reduce parts of cost matrix in the Hungerian method.
+%
+%[A,CH,RH]=hmreduce(A,CH,RH,LC,LR,SLC,SLR)
+%Input:
+%A   - Cost matrix.
+%CH  - vector of column of 'next zeros' in each row.
+%RH  - vector with list of unexplored rows.
+%LC  - column labels.
+%RC  - row labels.
+%SLC - set of column labels.
+%SLR - set of row labels.
+%
+%Output:
+%A   - Reduced cost matrix.
+%CH  - Updated vector of 'next zeros' in each row.
+%RH  - Updated vector of unexplored rows.
+
+% v1.0  96-06-14. Niclas Borlin, niclas@cs.umu.se.
+
+n=size(A,1);
+
+% Find which rows are covered, i.e. unlabelled.
+coveredRows=LR==0;
+
+% Find which columns are covered, i.e. labelled.
+coveredCols=LC~=0;
+
+r=find(~coveredRows);
+c=find(~coveredCols);
+
+% Get minimum of uncovered elements.
+m=min(min(A(r,c)));
+
+% Subtract minimum from all uncovered elements.
+A(r,c)=A(r,c)-m;
+
+% Check all uncovered columns..
+for j=c
+    % ...and uncovered rows in path order..
+    for i=SLR
+        % If this is a (new) zero..
+        if (A(i,j)==0)
+            % If the row is not in unexplored list..
+            if (RH(i)==0)
+                % ...insert it first in unexplored list.
+                RH(i)=RH(n+1);
+                RH(n+1)=i;
+                % Mark this zero as "next free" in this row.
+                CH(i)=j;
+            end
+            % Find last unassigned zero on row I.
+            row=A(i,:);
+            colsInList=-row(row<0);
+            if (length(colsInList)==0)
+                % No zeros in the list.
+                l=n+1;
+            else
+                l=colsInList(row(colsInList)==0);
+            end
+            % Append this zero to end of list.
+            A(i,l)=-j;
+        end
+    end
+end
+
+% Add minimum to all doubly covered elements.
+r=find(coveredRows);
+c=find(coveredCols);
+
+% Take care of the zeros we will remove.
+[i,j]=find(A(r,c)<=0);
+
+i=r(i);
+j=c(j);
+
+for k=1:length(i)
+    % Find zero before this in this row.
+    lj=find(A(i(k),:)==-j(k));
+    % Link past it.
+    A(i(k),lj)=A(i(k),j(k));
+    % Mark it as assigned.
+    A(i(k),j(k))=0;
+end
+
+A(r,c)=A(r,c)+m;
diff --git a/sourcecodes/bnt-master/KPMtools/image_rgb.m b/sourcecodes/bnt-master/KPMtools/image_rgb.m
new file mode 100644
index 00000000..e8d65883
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/image_rgb.m
@@ -0,0 +1,36 @@
+function image_rgb(M)
+% Show a matrix of integers as a color image.
+% This is like imagesc, except we know what the mapping is from integer to color.
+% If entries of M contain integers in {1,2,3}, we map
+% this to red/green/blue 
+
+cmap = [1 0 0; % red
+	0 1 0; % green
+	0 0 1; % blue
+	127/255 1 212/255]; % aquamarine
+image(M)
+set(gcf,'colormap', cmap);
+
+if 1
+  % make dummy handles, one per object type, for the legend
+  str = {};
+  for i=1:size(cmap,1)
+    dummy_handle(i) = line([0 0.1], [0 0.1]);
+    set(dummy_handle(i), 'color', cmap(i,:));
+    set(dummy_handle(i), 'linewidth', 2);
+    str{i} = num2str(i);
+  end
+  legend(dummy_handle, str, -1);
+end
+
+if 0
+[nrows ncols] = size(M);
+img = zeros(nrows, ncols, 3);
+for r=1:nrows
+  for c=1:ncols
+    q = M(r,c);
+    img(r,c,q) = 1;
+  end
+end
+image(img)
+end
diff --git a/sourcecodes/bnt-master/KPMtools/imresizeAspect.m b/sourcecodes/bnt-master/KPMtools/imresizeAspect.m
new file mode 100644
index 00000000..a69a2de4
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/imresizeAspect.m
@@ -0,0 +1,44 @@
+function img = imresizeAspect(img, maxSize)
+% function img = imresizeAspect(img, maxSize)
+% If image is larger than max size, reduce size, preserving aspect ratio of input.
+%
+% If size(input) = [y x] and maxSize = [yy xx],
+% then size(output) is given by the following (where a=y/x)
+%  if y<yy & x<xx  then [y x] 
+%  else if a<1 then [a*xx xx] 
+%  else [yy yy/a] 
+
+% For why we use bilinear,
+% See http://nickyguides.digital-digest.com/bilinear-vs-bicubic.htm
+
+if isempty(maxSize), return; end
+
+[y x c] = size(img);
+a= y/x;
+yy = maxSize(1); xx = maxSize(2); 
+if y <= yy & x <= xx
+  % no-op
+else
+  if a < 1
+    img = imresize(img, ceil([a*xx xx]), 'bilinear');
+  else
+    img = imresize(img, ceil([yy yy/a]), 'bilinear');
+  end
+  fprintf('resizing from %dx%d to %dx%d\n', y, x, size(img,1), size(img,2));
+end
+
+
+%test
+if 0
+  maxSize = [240 320];
+  %img = imread('C:\Images\Wearables\web_static_office\8.jpg'); 
+  %img = imread('C:\Images\Wearables\web_static_office\billandkirsten.jpg'); 
+  %img = imread('C:\Images\Wearables\web_static_street_april\p5.jpg'); 
+  img = imread('C:\Images\Wearables\Database_static_street\art11.jpg'); 
+  img2 = imresizeAspect(img, maxSize);
+  figure(1); clf; imshow(img)
+  figure(2); clf; imshow(img2)
+  fprintf('%dx%d (%5.3f) to %dx%d (%5.3f)\n', ...
+	  size(img,1), size(img,2), size(img,1)/size(img,2), ...
+	  size(img2,1), size(img2,2), size(img2,1)/size(img2,2));
+end
diff --git a/sourcecodes/bnt-master/KPMtools/ind2subv.m b/sourcecodes/bnt-master/KPMtools/ind2subv.m
new file mode 100644
index 00000000..6d9c4308
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/ind2subv.m
@@ -0,0 +1,22 @@
+function sub = ind2subv(siz,index)
+%IND2SUBV   Subscript vector from linear index.
+% IND2SUBV(SIZ,IND) returns a vector of the equivalent subscript values 
+% corresponding to a single index into an array of size SIZ.
+% If IND is a vector, then the result is a matrix, with subscript vectors
+% as rows.
+
+%sub = ind2subvTest(siz, index);
+n = length(siz);
+if n==0, sub = index; return; end % added by KPM 17 Nov 07
+cum_size = cumprod(siz(:)');
+prev_cum_size = [1 cum_size(1:end-1)];
+index = index(:) - 1;
+sub = rem(repmat(index,1,n),repmat(cum_size,length(index),1));
+sub = floor(sub ./ repmat(prev_cum_size,length(index),1))+1;
+
+% slow way
+%for dim = n:-1:1
+%  sub(:,dim) = floor(index/cum_size(dim))+1;
+%  index = rem(index,cum_size(dim));
+%end
+
diff --git a/sourcecodes/bnt-master/KPMtools/ind2subvKPM.c b/sourcecodes/bnt-master/KPMtools/ind2subvKPM.c
new file mode 100644
index 00000000..63a106a1
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/ind2subvKPM.c
@@ -0,0 +1,176 @@
+/* C mex version of ind2subv.m in misc directory */
+/* 2 input, 1 output         */
+/* siz, ndx                  */
+/* sub                       */
+
+#include "mex.h"
+#include <math.h>
+
+void rbinary(int num, int n, double *rbits){
+	int i, mask;
+	num = num - 1;
+
+	mask = 1 << (n-1); /* mask = 00100...0 , where the 1 is in column n (rightmost = col 1) */
+	for (i = 0; i < n; i++) {
+		rbits[n-i-1] = ((num & mask) == 0) ? 1 : 2;
+		num <<= 1;
+	}
+}
+
+void ind_subv(int num, const double *sizes, int n, double *rbits){
+	int i;
+	int *cumprod;
+
+	cumprod  = malloc(n * sizeof(int));
+	num = num - 1;
+	cumprod[0] = 1;
+	for (i = 0; i < n-1; i++)
+	cumprod[i+1] = cumprod[i] * (int)sizes[i];
+	for (i = n-1; i >= 0; i--) {
+		rbits[i] = ((int)floor(num / cumprod[i])) + 1;
+		num = num % cumprod[i];
+	}
+	free(cumprod);
+}
+
+
+void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[]){
+	int    i, j, k, nCol, nRow, nnRow, binary, count, temp, temp1, start;
+	double *pSize, *pNdx, *pr;
+	double ndx;
+	int    *subv, *cumprod, *templai;
+
+	pSize = mxGetPr(prhs[0]);
+	pNdx = mxGetPr(prhs[1]);
+	nCol = mxGetNumberOfElements(prhs[0]);
+	nnRow = mxGetNumberOfElements(prhs[1]);
+
+	nRow = 1;
+	for(i=0; i<nCol; i++){
+		nRow *= (int)pSize[i];
+	}
+
+	if(nCol == 0){
+		plhs[0] = mxDuplicateArray(prhs[1]);
+		return;
+	}
+
+	binary = 2;
+	for (i = 0; i < nCol; i++){
+		if (pSize[i] > 2.0){
+			binary = 0;
+			break;
+		}
+		else if((int)pSize[i] == 1){
+			binary = 1;
+		}
+	}
+
+	if(nnRow == 1){
+		ndx = mxGetScalar(prhs[1]);
+		plhs[0] = mxCreateDoubleMatrix(1, nCol, mxREAL);
+		pr = mxGetPr(plhs[0]);
+		if(binary == 2)rbinary((int)ndx, nCol, pr);
+		else ind_subv((int)ndx, pSize, nCol, pr);
+		return;
+	}
+
+	plhs[0] = mxCreateDoubleMatrix(nnRow, nCol, mxREAL);
+	pr = mxGetPr(plhs[0]);
+
+	subv = malloc(nRow * nCol * sizeof(int));
+
+	if (binary == 2) {
+		for(j=0; j<nCol; j++){
+			temp = (1 << j);
+			temp1 = j * nRow;
+			for(i=0; i<nRow; i++){
+				subv[temp1 + i] = ((i & temp) == 0) ? 1 : 2;
+			}
+		}
+	}
+	else if(binary == 1){
+		cumprod = (int *)malloc(nCol * sizeof(int));
+		templai = (int *)malloc(nCol * sizeof(int));
+		cumprod[0] = 1;
+		templai[0] = nRow;
+		for(i=1; i<nCol; i++){
+			k = (int)pSize[i-1] - 1;
+			cumprod[i] = cumprod[i-1] << k;
+			templai[i] = templai[i-1] >> k;
+		}
+		for(j=0; j<nCol; j++){
+			temp1 = j * nRow;
+			if(pSize[j] == 1.0){
+				for(i=0; i<nRow; i++){
+					subv[temp1 + i] = 1;
+				}
+			}
+			else{
+				temp = 1;
+				count = 0;
+				for(i=0; i<templai[j]; i++){
+					if(temp > 2) temp = 1;
+					for(k=0; k<cumprod[j]; k++){
+						subv[temp1 + count] = temp;
+                        count++;
+					}
+					temp++;
+				}
+			}
+		}
+		free(templai);
+		free(cumprod);
+	}
+	else {
+		cumprod = (int *)malloc(nCol * sizeof(int));
+		templai = (int *)malloc(nCol * sizeof(int));
+		cumprod[0] = 1;
+		for(i=1; i<nCol; i++){
+			cumprod[i] = (int)(cumprod[i-1] * pSize[i-1]);
+		}
+		templai[0] = nRow;
+		for(i=1; i<nCol; i++){
+			templai[i] = nRow / cumprod[i];
+		}
+		for(j=0; j<nCol; j++){
+			temp1 = j * nRow;
+			if(pSize[j] == 1.0){
+				for(i=0; i<nRow; i++){
+					subv[temp1 + i] = 1;
+				}
+			}
+			else{
+				temp = 1;
+				count = 0;
+				for(i=0; i<templai[j]; i++){
+					if(temp > (int)pSize[j]) temp = 1;
+					for(k=0; k<cumprod[j]; k++){
+						subv[temp1 + count] = temp;
+						count++;
+					}
+					temp++;
+				}
+			}
+		}
+		free(cumprod);
+		free(templai);
+	}
+
+	count = 0;
+	for(j=0; j<nCol; j++){
+		temp1 = j * nRow;
+		for(i=0; i<nnRow; i++){
+			start = (int)pNdx[i] - 1;
+			pr[count] = subv[temp1 + start];
+			count++;
+		}
+	}
+	free(subv);
+}
+
+
+
+
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/ind2subvKPM.m b/sourcecodes/bnt-master/KPMtools/ind2subvKPM.m
new file mode 100644
index 00000000..da178c7b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/ind2subvKPM.m
@@ -0,0 +1,57 @@
+function sub = ind2subvKPM(siz, ndx)
+% IND2SUBV Like the built-in ind2sub, but returns the answer as a row vector.
+% sub = ind2subv(siz, ndx)
+%
+% siz and ndx can be row or column vectors.
+% sub will be of size length(ndx) * length(siz).
+%
+% Example
+% ind2subv([2 2 2], 1:8) returns
+%  [1 1 1
+%   2 1 1
+%   ...
+%   2 2 2]
+% That is, the leftmost digit toggle fastest.
+%
+% See also SUBV2IND
+
+n = length(siz);
+
+
+if  n==0
+  sub = ndx;
+  return;
+end  
+
+if all(siz==2)
+  sub = dec2bitv(ndx-1, n);
+  sub = sub(:,n:-1:1)+1;
+  return;
+end
+
+cp = [1 cumprod(siz(:)')];
+ndx = ndx(:) - 1;
+sub = zeros(length(ndx), n);
+for i = n:-1:1 % i'th digit
+  sub(:,i) = floor(ndx/cp(i))+1;
+  ndx = rem(ndx,cp(i));
+end
+
+
+
+%%%%%%%%%%
+
+function bits = dec2bitv(d,n)
+% DEC2BITV Convert a decimal integer to a bit vector.
+% bits = dec2bitv(d,n) is just like the built-in dec2bin, except the answer is a vector, not a string.
+% n is an optional minimum length on the bit vector.
+% If d is a vector,  each row of the output array will be a bit vector.
+
+
+if (nargin<2)
+  n=1; % Need at least one digit even for 0.
+end
+d = d(:);
+
+[f,e]=log2(max(d)); % How many digits do we need to represent the numbers?
+bits=rem(floor(d*pow2(1-max(n,e):0)),2);
diff --git a/sourcecodes/bnt-master/KPMtools/ind2subvMinka.m b/sourcecodes/bnt-master/KPMtools/ind2subvMinka.m
new file mode 100644
index 00000000..4f2bcbef
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/ind2subvMinka.m
@@ -0,0 +1,23 @@
+function sub = ind2subvMinka(siz,index)
+%IND2SUBV   Subscript vector from linear index.
+% IND2SUBV(SIZ,IND) returns a vector of the equivalent subscript values 
+% corresponding to a single index into an array of size SIZ.
+% If IND is a vector, then the result is a matrix, with subscript vectors
+% as rows.
+
+% Written by Tom Minka
+% (c) Microsoft Corporation. All rights reserved.
+
+n = length(siz);
+if n==0, sub = index; return; end % added by KPM 17 Nov 07
+cum_size = cumprod(siz(:)');
+prev_cum_size = [1 cum_size(1:end-1)];
+index = index(:) - 1;
+sub = rem(repmat(index,1,n),repmat(cum_size,length(index),1));
+sub = floor(sub ./ repmat(prev_cum_size,length(index),1))+1;
+
+% slow way
+%for dim = n:-1:1
+%  sub(:,dim) = floor(index/cum_size(dim))+1;
+%  index = rem(index,cum_size(dim));
+%end
diff --git a/sourcecodes/bnt-master/KPMtools/ind2subvTest.m b/sourcecodes/bnt-master/KPMtools/ind2subvTest.m
new file mode 100644
index 00000000..53312a3b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/ind2subvTest.m
@@ -0,0 +1,10 @@
+function sub = ind2subvTest(siz,index)
+%IND2SUBV   Subscript vector from linear index.
+% IND2SUBV(SIZ,IND) returns a vector of the equivalent subscript values 
+% corresponding to a single index into an array of size SIZ.
+% If IND is a vector, then the result is a matrix, with subscript vectors
+% as rows.
+
+sub = ind2subvMinka(siz, index);
+subKPM = ind2subvKPM(siz, index);
+assert(isequal(sub, subKPM))
diff --git a/sourcecodes/bnt-master/KPMtools/initFigures.m b/sourcecodes/bnt-master/KPMtools/initFigures.m
new file mode 100644
index 00000000..6161b50e
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/initFigures.m
@@ -0,0 +1,48 @@
+% initFigures
+% Position 6 figures on the edges of the screen.
+% [xmin ymin w h] where (0,0) = bottom left
+% Numbers assume screen resolution is 1024 x 1280
+
+global FIGNUM NUMFIGS
+FIGNUM = 1; NUMFIGS = 6;
+
+screenMain = true; % set to false if initializing figures for second screen
+%screenMain = false;
+
+if screenMain
+  xoff = 0; 
+else
+  %xoff = 1280;
+  xoff = -1280;
+end
+
+% 2 x 3 design
+w = 400; h = 300;
+xs = [10 450 875] + xoff;
+ys = [650 40];
+
+if 0
+% 3x3 design
+w = 350; h = 250;
+xs = [10 380 750]+xoff;
+ys = [700 350 10];
+end
+
+
+Nfigs = length(xs)*length(ys);
+if screenMain
+  fig = 1; 
+else
+  fig = Nfigs + 1;
+end
+
+for yi=1:length(ys)
+  for xi=1:length(xs)
+    figure(fig);
+    set(gcf, 'position', [xs(xi) ys(yi) w h]);
+    fig = fig + 1;
+  end
+end
+
+% To plot something on the next available figure (with wrap around), use
+% sfigure(FIGNUM); clf; FIGNUM = wrap(FIGNUM+1, NUMFIGS); 
diff --git a/sourcecodes/bnt-master/KPMtools/installC_KPMtools.m b/sourcecodes/bnt-master/KPMtools/installC_KPMtools.m
new file mode 100644
index 00000000..b09271af
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/installC_KPMtools.m
@@ -0,0 +1,9 @@
+mex ind2subv.c
+mex subv2ind.c
+mex normalise.c
+mex -c mexutil.c
+if ~isunix 
+  mex repmatC.c mexutil.obj
+else
+  mex repmatC.c mexutil.o
+end
diff --git a/sourcecodes/bnt-master/KPMtools/is_psd.m b/sourcecodes/bnt-master/KPMtools/is_psd.m
new file mode 100644
index 00000000..ff3baa54
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/is_psd.m
@@ -0,0 +1,11 @@
+function b = positive_semidefinite(M)
+%
+% Return true iff v M v' >= 0 for any vector v.
+% We do this by checking that all the eigenvalues are non-negative.
+
+E = eig(M);
+if length(find(E>=0)) == length(E)
+  b = 1;
+else
+  b = 0;
+end
diff --git a/sourcecodes/bnt-master/KPMtools/is_stochastic.m b/sourcecodes/bnt-master/KPMtools/is_stochastic.m
new file mode 100644
index 00000000..4169f2cd
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/is_stochastic.m
@@ -0,0 +1,5 @@
+function p = is_stochastic(T)
+% IS_STOCHASTIC Is the argument a stochastic matrix, i.e., the sum over the last dimension is 1.
+% p = is_stochastic(T)
+
+p = approxeq(T, mk_stochastic(T));
diff --git a/sourcecodes/bnt-master/KPMtools/isemptycell.m b/sourcecodes/bnt-master/KPMtools/isemptycell.m
new file mode 100644
index 00000000..a8e5f943
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/isemptycell.m
@@ -0,0 +1,16 @@
+function E = isemptycell(C)
+% ISEMPTYCELL Apply the isempty function to each element of a cell array
+% E = isemptycell(C)
+%
+% This is equivalent to E = cellfun('isempty', C),
+% where cellfun is a function built-in to matlab version 5.3 or newer.
+
+if 0 % all(version('-release') >= 12)
+  E = cellfun('isempty', C);
+else
+  E = zeros(size(C));
+  for i=1:prod(size(C))
+    E(i) = isempty(C{i});
+  end
+  E = logical(E);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/isequalKPM.m b/sourcecodes/bnt-master/KPMtools/isequalKPM.m
new file mode 100644
index 00000000..2a6a2587
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/isequalKPM.m
@@ -0,0 +1,7 @@
+function p = isequalKPM(a,b)
+
+if isempty(a) & isempty(b)
+  p = 1;
+else
+  p = isequal(a,b);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/isposdef.m b/sourcecodes/bnt-master/KPMtools/isposdef.m
new file mode 100644
index 00000000..56f61967
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/isposdef.m
@@ -0,0 +1,9 @@
+function b = isposdef(a)
+% ISPOSDEF   Test for positive definite matrix.
+%    ISPOSDEF(A) returns 1 if A is positive definite, 0 otherwise.
+%    Using chol is much more efficient than computing eigenvectors.
+
+%  From Tom Minka's lightspeed toolbox
+
+[R,p] = chol(a);
+b = (p == 0);
diff --git a/sourcecodes/bnt-master/KPMtools/isscalarBNT.m b/sourcecodes/bnt-master/KPMtools/isscalarBNT.m
new file mode 100644
index 00000000..557d169d
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/isscalarBNT.m
@@ -0,0 +1,5 @@
+function p = isscalarBNT(v)
+% ISSCALAR Returns 1 if all dimensions have size 1.
+% p = isscalar(v)
+
+p = (prod(size(v))==1);
diff --git a/sourcecodes/bnt-master/KPMtools/isvectorBNT.m b/sourcecodes/bnt-master/KPMtools/isvectorBNT.m
new file mode 100644
index 00000000..5bb367a6
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/isvectorBNT.m
@@ -0,0 +1,9 @@
+function p = isvectorBNT(v)
+% ISVECTOR Returns 1 if all but one dimension have size 1.
+% p = isvector(v)
+%
+% Example: isvector(rand(1,2,1)) = 1, isvector(rand(2,2)) = 0.
+
+s=size(v);
+p = (ndims(v)<=2) & (s(1) == 1 | s(2) == 1);
+%p = sum( size(v) > 1) <= 1; % Peter Acklam's solution
diff --git a/sourcecodes/bnt-master/KPMtools/junk.c b/sourcecodes/bnt-master/KPMtools/junk.c
new file mode 100644
index 00000000..13624021
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/junk.c
@@ -0,0 +1,67 @@
+
+  m  = mxGetM(prhs[0]);
+  n  = mxGetN(prhs[0]);
+  pr = mxGetPr(prhs[0]);
+  pi = mxGetPi(prhs[0]);
+  cmplx = (pi == NULL ? 0 : 1);
+
+  /* Allocate space for sparse matrix. 
+   * NOTE:  Assume at most 20% of the data is sparse.  Use ceil
+   * to cause it to round up. 
+   */
+
+  percent_sparse = 0.2;
+  nzmax = (int)ceil((double)m*(double)n*percent_sparse);
+
+  plhs[0] = mxCreateSparse(m,n,nzmax,cmplx);
+  sr  = mxGetPr(plhs[0]);
+  si  = mxGetPi(plhs[0]);
+  irs = mxGetIr(plhs[0]);
+  jcs = mxGetJc(plhs[0]);
+    
+  /* Copy nonzeros. */
+  k = 0; 
+  isfull = 0;
+  for (j = 0; (j < n); j++) {
+    int i;
+    jcs[j] = k;
+    for (i = 0; (i < m); i++) {
+      if (IsNonZero(pr[i]) || (cmplx && IsNonZero(pi[i]))) {
+
+        /* Check to see if non-zero element will fit in 
+         * allocated output array.  If not, increase
+         * percent_sparse by 10%, recalculate nzmax, and augment
+         * the sparse array.
+         */
+        if (k >= nzmax) {
+          int oldnzmax = nzmax;
+          percent_sparse += 0.1;
+          nzmax = (int)ceil((double)m*(double)n*percent_sparse);
+
+          /* Make sure nzmax increases atleast by 1. */
+          if (oldnzmax == nzmax) 
+            nzmax++;
+
+          mxSetNzmax(plhs[0], nzmax); 
+          mxSetPr(plhs[0], mxRealloc(sr, nzmax*sizeof(double)));
+          if (si != NULL)
+          mxSetPi(plhs[0], mxRealloc(si, nzmax*sizeof(double)));
+          mxSetIr(plhs[0], mxRealloc(irs, nzmax*sizeof(int)));
+
+          sr  = mxGetPr(plhs[0]);
+          si  = mxGetPi(plhs[0]);
+          irs = mxGetIr(plhs[0]);
+        }
+        sr[k] = pr[i];
+        if (cmplx) {
+          si[k] = pi[i];
+        }
+        irs[k] = i;
+        k++;
+      }
+    }
+    pr += m;
+    pi += m;
+  }
+  jcs[n] = k;
+}
diff --git a/sourcecodes/bnt-master/KPMtools/loadcell.m b/sourcecodes/bnt-master/KPMtools/loadcell.m
new file mode 100644
index 00000000..85691854
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/loadcell.m
@@ -0,0 +1,153 @@
+function [lc,dflag,dattype]=loadcell(fname,delim,exclusions,options);
+%function [lc,dflag,numdata]=loadcell(fname,delim,exclusions);
+%  
+%  loadcell loads a cell array with character delimited
+%  data, which can have variable length lines and content.
+%  Numeric values are converted from string to double 
+%  unless options is a string containing 'string'.
+%  
+%  loadcell is for use with small datasets. It is not optimised
+%  for large datasets.
+% 
+%  fname is the filename to be loaded
+%
+%  delim is/are the relevant delimiter(s). If char(10) is included
+%  newlines are simply treated as delimiters and a 1-d array is created.
+%
+%  exclusions  are the set of characters to be treated as paired
+%    braces: line ends or delimiters within braces are ignored.
+%    braces are single characters and any brace can pair with 
+%    any other brace: no type pair checking is done.
+%
+%  options can be omitted or can contain 'string' if no numeric
+%    conversion is required, 'single' if multiple adjacent seperators
+%    should not be treated as one, 'free' if all linefeeds should be stripped
+%    first and 'empty2num' if empty fields are to be treated as numeric 
+%    zeros rather than an empty character set. Combine options using 
+%    concatenation.
+%
+%  lc is a cell array containing the loaded data.
+%
+%  dflag is a set of flags denoting the (i,j) values where data was entered
+%  dflag(i,j)=1 implies lc(i,j) was loaded from the data, and not just set
+%  to empty, say, by default.
+%
+%  numdata is an array  numdata(i,j)=NaN implies
+%    lc(i,j) is a string, otherwise it stores the number at i,j.
+%    This will occur regardless of whether the 'string' option is set.
+%
+%  lc will return -1 if the file is not found or could not be
+%  opened.
+%
+%  Hint: numdata+(1/dflag-1) provides a concise descriptor for the numeric data
+%  Inf=not loaded
+%  NaN=was string or empty set.
+%  otherwise numeric
+%
+%  EXAMPLE
+%
+%[a,b]=loadcell('resultsfile',[',' char(9)],'"','single-string');
+%   will load file 'resultsfile' into variable a, treating any of tab or 
+%   comma as delimiters. Delimiters or carriage returns lying 
+%   between two double inverted commas will be ignored. Two adjacent delimiters
+%   will count twice, and all data will be kept as a string.
+%
+%   Note: in space-separated data 'single' would generally be omitted,
+%   wheras in comma-seperated data it would be included.
+%  
+%   Note the exclusion characters will remain in the final data, and any data
+%   contained within or containing exclusion characters will not be 
+%   converted to numerics.
+%
+%   (c) Amos Storkey 2002
+%    v b160702
+
+% MATLAB is incapable of loading variable length lines or variable type values
+% with a whole file command under the standard library sets. This mfile 
+% fills that gap.
+if (nargin<4) 
+    options=' ';
+end;
+dflag = [];
+%Open file
+fid=fopen(fname,'rt');
+%Cannot open: return -1
+if (fid<0)
+  lc=-1;
+else
+  fullfile=fread(fid,'uchar=>char')';
+  %Strip LF if free is set
+  if ~isempty(findstr(options,'free'))
+      fullfile=strrep(fullfile,char(10),'');
+  end;
+  %Find all delimiters
+  delimpos=[];
+  for s=1:length(delim)
+    delimpos=[delimpos find(fullfile==delim(s))];
+  end
+  %Find all eol
+  endpos=find(fullfile==char(10));
+  endpos=setdiff(endpos,delimpos);
+  %find all exclusions
+  xclpos=[];
+  for s=1:length(exclusions);
+    xclpos=[xclpos find(fullfile==exclusions(s))];
+  end
+  sort(xclpos);
+  xclpos=[xclpos(1:2:end-1);xclpos(2:2:end)];
+  %Combine eol and delimiters
+  jointpos=union(delimpos,endpos);
+  t=1;
+  %Remove delim/eol within exclusion pairs
+  removedelim=[];
+  for s=1:length(jointpos)
+    if any((jointpos(s)>xclpos(1,:)) & (jointpos(s)<xclpos(2,:)))
+      removedelim(t)=jointpos(s);
+      t=t+1;
+    end;
+
+  end
+  %and add start point
+  jointpos=[0 setdiff(jointpos,removedelim)];
+  i=1;
+  j=1;
+  posind=1;
+  multflag=isempty(findstr(options,'single'));
+  stringflag=~isempty(findstr(options,'string'));
+  emptnum=~isempty(findstr(options,'empty2num'));
+  %Run through
+  while (posind<(length(jointpos)))
+    %Get current field
+    tempstr=fullfile(jointpos(posind)+1:jointpos(posind+1)-1);
+    %If empty only continue if adjacent delim count.
+    if ~(isempty(tempstr) & multflag);
+      %This ij is set
+      dflag(i,j)=1;
+      %Convert to num
+      tempno=str2double([tempstr]);
+      %If emptystring convert to zero if emptnum set
+      if (isempty(tempstr) & emptnum)
+          tempno=0;
+      end;
+      %Set dattype to no (or NaN if not a num
+      dattype(i,j)=tempno;
+      %If NaN set lc to string else to num if stringflag not set
+      if (isnan(tempno) |  stringflag) 
+        lc{i,j}=tempstr;
+      else
+        lc{i,j}=tempno;
+      end;
+      %Next j
+      j=j+1;
+    end;
+    %If eol inc i and reset j
+    if ismember(jointpos(posind+1),endpos)
+        i=i+1;
+        j=1;
+    end;
+    %Inc to next delim
+    posind=posind+1;      
+  end;
+end;
+%Logicalise dflag
+dflag=logical(dflag);
diff --git a/sourcecodes/bnt-master/KPMtools/logb.m b/sourcecodes/bnt-master/KPMtools/logb.m
new file mode 100644
index 00000000..aa77ddb9
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/logb.m
@@ -0,0 +1,5 @@
+function x = logb(y, base)
+% logb - logarithm to base b
+% function x = logb(y, base)
+
+x = log(y) ./ log(base);
diff --git a/sourcecodes/bnt-master/KPMtools/logdet.m b/sourcecodes/bnt-master/KPMtools/logdet.m
new file mode 100644
index 00000000..cfff98d2
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/logdet.m
@@ -0,0 +1,8 @@
+function y = logdet(A)
+% log(det(A)) where A is positive-definite.
+% This is faster and more stable than using log(det(A)).
+
+%  From Tom Minka's lightspeed toolbox
+
+U = chol(A);
+y = 2*sum(log(diag(U)));
diff --git a/sourcecodes/bnt-master/KPMtools/logsum.m b/sourcecodes/bnt-master/KPMtools/logsum.m
new file mode 100644
index 00000000..1d8ae457
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/logsum.m
@@ -0,0 +1,28 @@
+function y=logsum(x,d)
+%LOGSUM logsum(x,d)=log(sum(exp(x),d))
+%  d gives dimension to sum along
+
+%      Copyright (C) Mike Brookes 1998
+%
+%      Last modified Mon Oct 12 15:47:25 1998
+%
+%   VOICEBOX is a MATLAB toolbox for speech processing. Home page is at
+%   http://www.ee.ic.ac.uk/hp/staff/dmb/voicebox/voicebox.html
+%
+
+if nargin==1
+   d=[find(size(x)-1) 1];
+   d=d(1);
+end
+n=size(x,d);
+if n<=1, y=x; return; end
+s=size(x);
+p=[d:ndims(x) 1:d-1];
+z=reshape(permute(x,p),n,prod(s)/n);
+
+y=max(z);
+y=y+log(sum(exp(z-y(ones(n,1),:))));
+
+s(d)=1;
+y=ipermute(reshape(y,s(p)),p);
+
diff --git a/sourcecodes/bnt-master/KPMtools/logsum_simple.m b/sourcecodes/bnt-master/KPMtools/logsum_simple.m
new file mode 100644
index 00000000..9af56669
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/logsum_simple.m
@@ -0,0 +1,23 @@
+function result = logsum(logv)
+
+len = length(logv);
+if (len<2);
+  error('Subroutine logsum cannot sum less than 2 terms.');
+end;
+
+% First two terms
+if (logv(2)<logv(1)),
+  result = logv(1) + log( 1 + exp( logv(2)-logv(1) ) );
+else,
+  result = logv(2) + log( 1 + exp( logv(1)-logv(2) ) );
+end;
+
+% Remaining terms
+for (i=3:len),
+  term = logv(i);
+  if (result<term),
+    result = term   + log( 1 + exp( result-term ) );
+  else,
+    result = result + log( 1 + exp( term-result ) );
+  end;    
+end
diff --git a/sourcecodes/bnt-master/KPMtools/logsum_test.m b/sourcecodes/bnt-master/KPMtools/logsum_test.m
new file mode 100644
index 00000000..d7c701db
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/logsum_test.m
@@ -0,0 +1,6 @@
+p1 = log(1e-5);
+p2 = log(5*1e-6);
+p3 = log(sum(exp([p1 p2])))
+p4 = logsumexp([p1 p2],2)
+p5 = logsum([p1 p2])
+p6 = logsum([p1 p2])
diff --git a/sourcecodes/bnt-master/KPMtools/logsumexp.m b/sourcecodes/bnt-master/KPMtools/logsumexp.m
new file mode 100644
index 00000000..b639cbb2
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/logsumexp.m
@@ -0,0 +1,24 @@
+function s = logsumexp(a, dim)
+% Returns log(sum(exp(a),dim)) while avoiding numerical underflow.
+% Default is dim = 1 (rows) or dim=2 for a row vector
+% logsumexp(a, 2) will sum across columns instead of rows
+
+% Written by Tom Minka, modified by Kevin Murphy
+
+if nargin < 2
+  dim = 1;
+  if ndims(a) <= 2 & size(a,1)==1
+    dim = 2;
+  end
+end
+
+% subtract the largest in each column
+[y, i] = max(a,[],dim);
+dims = ones(1,ndims(a));
+dims(dim) = size(a,dim);
+a = a - repmat(y, dims);
+s = y + log(sum(exp(a),dim));
+%i = find(~finite(y));
+%if ~isempty(i)
+%  s(i) = y(i);
+%end
diff --git a/sourcecodes/bnt-master/KPMtools/logsumexpv.m b/sourcecodes/bnt-master/KPMtools/logsumexpv.m
new file mode 100644
index 00000000..d8e4d8a7
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/logsumexpv.m
@@ -0,0 +1,15 @@
+function s = logsumexpv(a)
+% Returns log(sum(exp(a)))  while avoiding numerical underflow.
+%
+% e.g., log(e^a1 + e^a2) = a1 + log(1 + e^(a2-a1)) if a1>a2
+% If a1 ~ a2, and a1>a2, then e^(a2-a1) is exp(small negative number),
+% which can be computed without underflow.
+
+% Same as logsumexp, except we assume a is a vector.
+% This avoids a call to repmat, which takes 50% of the time!
+
+a = a(:)'; % make row vector
+m = max(a);
+b = a - m*ones(1,length(a));
+s = m + log(sum(exp(b)));
+
diff --git a/sourcecodes/bnt-master/KPMtools/mahal2conf.m b/sourcecodes/bnt-master/KPMtools/mahal2conf.m
new file mode 100644
index 00000000..e5535748
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mahal2conf.m
@@ -0,0 +1,60 @@
+% MAHAL2CONF - Translates a Mahalanobis distance into a confidence
+%              interval.  Consider a multivariate Gaussian
+%              distribution of the form
+%
+%   p(x) = 1/sqrt((2 * pi)^d * det(C)) * exp((-1/2) * MD(x, m, inv(C)))
+%
+%              where MD(x, m, P) is the Mahalanobis distance from x
+%              to m under P:
+%
+%                 MD(x, m, P) = (x - m) * P * (x - m)'
+%
+%              A particular Mahalanobis distance k identifies an
+%              ellipsoid centered at the mean of the distribution.
+%              The confidence interval associated with this ellipsoid
+%              is the probability mass enclosed by it.
+%
+%              If X is an d dimensional Gaussian-distributed vector,
+%              then the Mahalanobis distance of X is distributed
+%              according to the Chi-squared distribution with d
+%              degrees of freedom.  Thus, the confidence interval is
+%              determined by integrating the chi squared distribution
+%              up to the Mahalanobis distance of the measurement.
+%
+% Usage:
+% 
+%   c = mahal2conf(m, d);
+%
+% Inputs:
+%
+%   m    - the Mahalanobis radius of the ellipsoid
+%   d    - the number of dimensions of the Gaussian distribution
+%
+% Outputs:
+%
+%   c    - the confidence interval, i.e., the fraction of
+%          probability mass enclosed by the ellipsoid with the
+%          supplied Mahalanobis distance
+%
+% See also: CONF2MAHAL
+
+% Copyright (C) 2002 Mark A. Paskin
+%
+% This program is free software; you can redistribute it and/or modify
+% it under the terms of the GNU General Public License as published by
+% the Free Software Foundation; either version 2 of the License, or
+% (at your option) any later version.
+%
+% This program is distributed in the hope that it will be useful, but
+% WITHOUT ANY WARRANTY; without even the implied warranty of
+% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+% General Public License for more details.
+%
+% You should have received a copy of the GNU General Public License
+% along with this program; if not, write to the Free Software
+% Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+% USA.
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+function c = mahal2conf(m, d)
+
+c = chi2cdf(m, d);
\ No newline at end of file
diff --git a/sourcecodes/bnt-master/KPMtools/marg_table.m b/sourcecodes/bnt-master/KPMtools/marg_table.m
new file mode 100644
index 00000000..0f1e5be5
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/marg_table.m
@@ -0,0 +1,27 @@
+function smallT = marg_table(bigT, bigdom, bigsz, onto, maximize)
+% MARG_TABLE Marginalize a table
+% smallT = marg_table(bigT, bigdom, bigsz, onto, maximize)
+
+if nargin < 5, maximize = 0; end
+
+
+smallT = myreshape(bigT, bigsz); % make sure it is a multi-dim array
+sum_over = mysetdiff(bigdom, onto);
+ndx = find_equiv_posns(sum_over, bigdom);
+if maximize
+  for i=1:length(ndx)
+    smallT = max(smallT, [], ndx(i));
+  end
+else
+  for i=1:length(ndx)
+    smallT = sum(smallT, ndx(i));
+  end
+end
+
+
+ns = zeros(1, max(bigdom));
+%ns(bigdom) = mysize(bigT); % ignores trailing dimensions of size 1
+ns(bigdom) = bigsz;
+
+smallT = squeeze(smallT); % remove all dimensions of size 1
+smallT = myreshape(smallT, ns(onto)); % put back relevant dims of size 1
diff --git a/sourcecodes/bnt-master/KPMtools/marginalize_table.m b/sourcecodes/bnt-master/KPMtools/marginalize_table.m
new file mode 100644
index 00000000..adc5443c
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/marginalize_table.m
@@ -0,0 +1,50 @@
+function smallT = marginalize_table(bigT, bigdom, bigsz, onto, maximize)
+% MARG_TABLE Marginalize a table
+% function smallT = marginalize_table(bigT, bigdom, bigsz, onto, maximize)
+
+% Like marg_table in BNT, except we do not assume the domains are sorted
+
+if nargin < 5, maximize = 0; end
+
+
+smallT = myreshape(bigT, bigsz); % make sure it is a multi-dim array
+sum_over = mysetdiff(bigdom, onto);
+ndx = find_equiv_posns(sum_over, bigdom);
+if maximize
+  for i=1:length(ndx)
+    smallT = max(smallT, [], ndx(i));
+  end
+else
+  for i=1:length(ndx)
+    smallT = sum(smallT, ndx(i));
+  end
+end
+
+
+ns = zeros(1, max(bigdom));
+%ns(bigdom) = mysize(bigT); % ignores trailing dimensions of size 1
+ns(bigdom) = bigsz;
+
+% If onto has a different ordering than bigdom, the following
+% will produce the wrong results
+
+%smallT = squeeze(smallT); % remove all dimensions of size 1
+%smallT = myreshape(smallT, ns(onto)); % put back relevant dims of size 1
+
+% so permute dimensions to match desired ordering (as specified by onto)
+
+
+% like find_equiv_posns, but keeps ordering
+outdom = [onto sum_over];
+for i=1:length(outdom)
+  j = find(bigdom==outdom(i));
+  match(i) = j;
+end
+outdom = [onto sum_over];
+for i=1:length(outdom)
+  j = find(bigdom==outdom(i));
+  match(i) = j;
+end
+if match ~= 1
+  smallT = permute(smallT, match);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/matprint.m b/sourcecodes/bnt-master/KPMtools/matprint.m
new file mode 100644
index 00000000..e05c5f40
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/matprint.m
@@ -0,0 +1,36 @@
+% MATPRINT - prints a matrix with specified format string
+%
+% Usage: matprint(a, fmt, fid)
+%
+%                 a   - Matrix to be printed.
+%                 fmt - C style format string to use for each value.
+%                 fid - Optional file id.
+%
+% Eg. matprint(a,'%3.1f') will print each entry to 1 decimal place
+
+% Peter Kovesi
+% School of Computer Science & Software Engineering
+% The University of Western Australia
+% pk @ csse uwa edu au
+% http://www.csse.uwa.edu.au/~pk
+%
+% March 2002
+
+function matprint(a, fmt, fid)
+    
+    if nargin < 3
+	fid = 1;
+    end
+    
+    [rows,cols] = size(a);
+    
+    % Construct a format string for each row of the matrix consisting of
+    % 'cols' copies of the number formating specification
+    fmtstr = [];
+    for c = 1:cols
+      fmtstr = [fmtstr, ' ', fmt];
+    end
+    fmtstr = [fmtstr '\n'];    % Add a line feed
+    
+    fprintf(fid, fmtstr, a');  % Print the transpose of the matrix because
+                               % fprintf runs down the columns of a matrix.
\ No newline at end of file
diff --git a/sourcecodes/bnt-master/KPMtools/max_mult.c b/sourcecodes/bnt-master/KPMtools/max_mult.c
new file mode 100644
index 00000000..204fd956
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/max_mult.c
@@ -0,0 +1,46 @@
+/* C mex version of max_mult.m in BPMRF2 directory  */
+/* gcc -Wall -I/mit/matlab_v6.5/distrib/bin/glnx86 -c max_mult.c */
+
+#include <math.h>
+#include "mex.h"
+
+void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
+{
+  int rows,cols,common,m,n,p;
+  double y1, y2;
+  double *arr1, *arr2, *arr3;
+
+
+  if (nrhs!=2 || nlhs>1)
+    mexErrMsgTxt("max_mult requires two inputs and one output");
+  if (mxIsChar(prhs[0]) || mxIsClass(prhs[0], "sparse") || mxIsComplex(prhs[0])
+      || mxIsChar(prhs[1]) || mxIsClass(prhs[1], "sparse") || mxIsComplex(prhs[1]))
+    mexErrMsgTxt("Inputs must be real, full, and nonstring");
+  if (mxGetN(prhs[0])!=mxGetM(prhs[1]))
+    mexErrMsgTxt("The number of columns of A must be the same as the number of rows of x");
+  
+
+  arr1=mxGetPr(prhs[0]);
+  arr2=mxGetPr(prhs[1]);
+  p=mxGetN(prhs[0]);
+  m=mxGetM(prhs[0]);
+  n=mxGetN(prhs[1]);
+  plhs[0]=mxCreateDoubleMatrix(m, n, mxREAL);
+  arr3=mxMalloc(m*n*sizeof(double));
+
+  for (rows=0; rows<m ; rows++)
+    for (cols=0; cols<n ; cols++)
+    {
+      y1=arr1[rows]*arr2[cols*p];  
+      for (common=1; common<p; common++)
+      {
+	y2=arr1[rows+common*m]*arr2[common+cols*p];
+        if (y2>y1)
+          y1=y2;
+      }
+      arr3[rows+cols*m]=y1;
+    }
+
+  mxSetPr(plhs[0], arr3);
+	 
+}
diff --git a/sourcecodes/bnt-master/KPMtools/max_mult.m b/sourcecodes/bnt-master/KPMtools/max_mult.m
new file mode 100644
index 00000000..fab37e3a
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/max_mult.m
@@ -0,0 +1,21 @@
+function y=max_mult(A,x)
+% MAX_MULT Like matrix multiplication, but sum gets replaced by max
+% function y=max_mult(A,x) y(i) = max_j A(i,j) x(j)
+
+%X=ones(size(A,1),1) * x(:)'; % X(j,i) = x(i)
+%y=max(A.*X, [], 2);
+
+% This is faster
+if size(x,2)==1
+  X=x*ones(1,size(A,1)); % X(i,j) = x(i)
+  y=max(A'.*X)';
+else
+%this works for arbitrarily sized A and x (but is ugly, and slower than above)
+  X=repmat(x, [1 1 size(A,1)]);
+  B=repmat(A, [1 1 size(x,2)]);
+  C=permute(B,[2 3 1]);
+  y=permute(max(C.*X),[3 2 1]);
+%  this is even slower, as is using squeeze instead of permute
+%  Y=permute(X, [3 1 2]);
+%  y=permute(max(Y.*B, [], 2), [1 3 2]);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/mexutil.c b/sourcecodes/bnt-master/KPMtools/mexutil.c
new file mode 100644
index 00000000..b2bd3e7d
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mexutil.c
@@ -0,0 +1,43 @@
+#include "mexutil.h"
+
+/* Functions to create uninitialized arrays. */
+
+mxArray *mxCreateNumericArrayE(int ndim, const int *dims, 
+         mxClassID class, mxComplexity ComplexFlag)
+{
+  mxArray *a;
+  int i, *dims1 = mxMalloc(ndim*sizeof(int));
+  size_t sz = 1;
+  for(i=0;i<ndim;i++) {
+    sz *= dims[i];
+    dims1[i] = 1;
+  }
+  a = mxCreateNumericArray(ndim,dims1,class,ComplexFlag);
+  sz *= mxGetElementSize(a);
+  mxSetDimensions(a, dims, ndim);
+  mxFree(dims1);
+  mxSetData(a, mxRealloc(mxGetData(a), sz));
+  if(ComplexFlag == mxCOMPLEX) {
+    mxSetPi(a, mxRealloc(mxGetPi(a),sz));
+  }
+  return a;
+}
+mxArray *mxCreateNumericMatrixE(int m, int n, mxClassID class, 
+				mxComplexity ComplexFlag)
+{
+  size_t sz = m*n*sizeof(double);
+  mxArray *a = mxCreateNumericMatrix(1, 1, class, ComplexFlag);
+  mxSetM(a,m);
+  mxSetN(a,n);
+  mxSetPr(a, mxRealloc(mxGetPr(a),sz));
+  if(ComplexFlag == mxCOMPLEX) {
+    mxSetPi(a, mxRealloc(mxGetPi(a),sz));
+  }
+  return a;
+}
+mxArray *mxCreateDoubleMatrixE(int m, int n, 
+			       mxComplexity ComplexFlag)
+{
+  return mxCreateNumericMatrixE(m,n,mxDOUBLE_CLASS,ComplexFlag);
+}
+
diff --git a/sourcecodes/bnt-master/KPMtools/mexutil.h b/sourcecodes/bnt-master/KPMtools/mexutil.h
new file mode 100644
index 00000000..683156da
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mexutil.h
@@ -0,0 +1,8 @@
+#include "mex.h"
+
+mxArray *mxCreateNumericArrayE(int ndim, const int *dims, 
+			       mxClassID class, mxComplexity ComplexFlag);
+mxArray *mxCreateNumericMatrixE(int m, int n, mxClassID class, 
+				mxComplexity ComplexFlag);
+mxArray *mxCreateDoubleMatrixE(int m, int n, 
+			       mxComplexity ComplexFlag);
diff --git a/sourcecodes/bnt-master/KPMtools/mk_multi_index.m b/sourcecodes/bnt-master/KPMtools/mk_multi_index.m
new file mode 100644
index 00000000..5cb86d5d
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mk_multi_index.m
@@ -0,0 +1,23 @@
+function index = mk_multi_index(n, dims, vals)
+% MK_MULTI_INDEX Compute the indices of the submatrix where dims(i)=vals(i).
+% index = mk_multi_index(n, dims, vals)
+% 
+% Example:
+% index = mk_multi_index(3, [1 3], [3 2])
+% gives index = {3, ':', 2}, which will select out dim 1 = 3 and dim 3 = 2
+% So if A(:,:,1)=[1 2;3 4; 5 6]; A(:,:,2)=[7 8; 9 10; 11 12]
+% then A(index{:}) = [11 12]: 
+
+if n==0
+  index = { 1 };
+  return;
+end
+
+index = cell(1,n);
+for i=1:n
+  index{i} = ':';
+end
+for i=1:length(dims)
+  index{dims(i)} = vals(i);
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/mk_stochastic.m b/sourcecodes/bnt-master/KPMtools/mk_stochastic.m
new file mode 100644
index 00000000..68aac6ab
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mk_stochastic.m
@@ -0,0 +1,27 @@
+function [T,Z] = mk_stochastic(T)
+% MK_STOCHASTIC Ensure the argument is a stochastic matrix, i.e., the sum over the last dimension is 1.
+% [T,Z] = mk_stochastic(T)
+%
+% If T is a vector, it will sum to 1.
+% If T is a matrix, each row will sum to 1.
+% If T is a 3D array, then sum_k T(i,j,k) = 1 for all i,j.
+
+% Set zeros to 1 before dividing
+% This is valid since S(j) = 0 iff T(i,j) = 0 for all j
+
+if (ndims(T)==2) && (size(T,1)==1 || size(T,2)==1) % isvector
+  [T,Z] = normalise(T);
+elseif ndims(T)==2 % matrix
+  Z = sum(T,2); 
+  S = Z + (Z==0);
+  norm = repmat(S, 1, size(T,2));
+  T = T ./ norm;
+else % multi-dimensional array
+  ns = size(T);
+  T = reshape(T, prod(ns(1:end-1)), ns(end));
+  Z = sum(T,2);
+  S = Z + (Z==0);
+  norm = repmat(S, 1, ns(end));
+  T = T ./ norm;
+  T = reshape(T, ns);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/mkdirKPM.m b/sourcecodes/bnt-master/KPMtools/mkdirKPM.m
new file mode 100644
index 00000000..56c50567
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mkdirKPM.m
@@ -0,0 +1,24 @@
+function mkdirKPM(dname)
+% function mkdirKPM(dname)
+% If directory does not exist, make it
+% 
+% mkdirKPM('foo\bar\baz') makes subdirectories bar and baz
+% mkdirKPM('foo\bar\baz.txt') makes subdirectories bar 
+
+% convert foo\bar\baz to pathstr=foo\bar, name=baz
+% convert foo\bar\baz.txt to pathstr=foo\bar, name=baz
+[pathstr, name, ext, versn] = fileparts(dname);
+if ~isempty(ext) % we stripped off something after final period
+  % convert foo\bar to pathstr=foo, name=bar
+  % convert foo\bar.bad to pathstr=foo, name=bar.bad
+  [pathstr, name, ext, versn] = fileparts(pathstr);
+  name = sprintf('%s%s', name, ext); % in case there is a period in the directory name
+end
+
+dname = fullfile(pathstr, name);
+if ~exist(dname, 'dir')
+  %fprintf('mkdirKPM: making %s, %s \n', pathstr, name);
+  mkdir(pathstr, name)
+else
+  %fprintf('mkdirKPM: %s already exists\n', dname)
+end
diff --git a/sourcecodes/bnt-master/KPMtools/montageKPM.m b/sourcecodes/bnt-master/KPMtools/montageKPM.m
new file mode 100644
index 00000000..c0354d3c
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/montageKPM.m
@@ -0,0 +1,102 @@
+function h = montageKPM(arg)
+% montageKPM is like the built-in montage, but assumes input is MxNxK or filenames
+%
+% Converts patches (y,x,i) into patches(y,x,1,i)
+% Also, adds a black border aroudn them
+
+if iscell(arg)
+  h= montageFilenames(arg);
+else
+  nr = size(arg,1); nc = size(arg,2); Npatches = size(arg,3);
+  patchesColor = reshape(arg, [nr nc 1 Npatches]);
+  patchesColor = patchesColor ./ max(patchesColor(:));
+  
+  if 1
+    %put a black border around them for display purposes
+    border = 5;
+    bgColor = ones(1,1,class(patchesColor));
+    patchesColorBig = bgColor*ones(nr+2*border, nc+2*border, 1, Npatches, class(patchesColor));
+    %patchesColorBig = zeros(nr+2*border, nc+2*border, 1, Npatches, class(patchesColor));
+    patchesColorBig(border+1:end-border, border+1:end-border, :, :) = patchesColor;
+  else
+    patchesColorBig = patchesColor;
+  end
+  montage(patchesColorBig)
+
+end
+
+%%%%%%%%%%%%%
+
+function h = montageFilenames(filenames)
+
+%[nRows, nCols, nBands, nFrames] = size(a);
+
+% Estimate nMontageColumns and nMontageRows given the desired ratio of
+% Columns to Rows to be one (square montage).
+aspectRatio = 1; 
+nMontageCols = sqrt(aspectRatio * nRows * nFrames / nCols);
+
+% Make sure montage rows and columns are integers. The order in the adjustment
+% matters because the montage image is created horizontally across columns.
+nMontageCols = ceil(nMontageCols); 
+nMontageRows = ceil(nFrames / nMontageCols);
+
+% Create the montage image.
+b = a(1,1); % to inherit type 
+b(1,1) = 0; % from a
+b = repmat(b, [nMontageRows*nRows, nMontageCols*nCols, nBands, 1]);
+
+rows = 1 : nRows; 
+cols = 1 : nCols;
+
+for i = 0:nMontageRows-1
+  for j = 0:nMontageCols-1,
+    k = j + i * nMontageCols + 1;
+    if k <= nFrames
+      b(rows + i * nRows, cols + j * nCols, :) = a(:,:,:,k);
+    else
+      break;
+    end
+  end
+end
+
+if isempty(cm)
+  hh = imshow(b);
+else
+  hh = imshow(b,cm);
+end
+
+if nargout > 0
+    h = hh;
+end
+
+%--------------------------------------------------------------
+%Parse Inputs Function
+
+function [I,map] = parse_inputs(varargin)
+
+% initialize variables
+map = [];
+
+iptchecknargin(1,2,nargin,mfilename);
+iptcheckinput(varargin{1},{'uint8' 'double' 'uint16' 'logical' 'single' ...
+                    'int16'},{},mfilename, 'I, BW, or RGB',1);
+I = varargin{1};
+
+if nargin==2
+  if isa(I,'int16')
+    eid = sprintf('Images:%s:invalidIndexedImage',mfilename);
+    msg1 = 'An indexed image can be uint8, uint16, double, single, or ';
+    msg2 = 'logical.';
+    error(eid,'%s %s',msg1, msg2);
+  end
+  map = varargin{2};
+  iptcheckinput(map,{'double'},{},mfilename,'MAP',1);
+  if ((size(map,1) == 1) && (prod(map) == numel(I)))
+    % MONTAGE(D,[M N P]) OBSOLETE
+    eid = sprintf('Images:%s:obsoleteSyntax',mfilename);
+    msg1 = 'MONTAGE(D,[M N P]) is an obsolete syntax.';
+    msg2 = 'Use multidimensional arrays to represent multiframe images.';
+    error(eid,'%s\n%s',msg1,msg2);    
+  end
+end
diff --git a/sourcecodes/bnt-master/KPMtools/montageKPM2.m b/sourcecodes/bnt-master/KPMtools/montageKPM2.m
new file mode 100644
index 00000000..1bd521a9
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/montageKPM2.m
@@ -0,0 +1,69 @@
+function montageKPM2(data)
+% data(y,x,b,f) or data(y,x,f)
+% can be double - uses imagesc to display, not imshow
+% based on imaqmontage
+
+if ndims(data)==3
+  nr = size(data,1); nc = size(data,2); Npatches = size(data,3); Nbands = 1;
+  data = reshape(data, [nr nc Nbands Npatches]);
+else
+  nr = size(data,1); nc = size(data,2); Nbands = size(data,3); Npatches = size(data,4);
+end
+nativeVal = data(1, 1);
+dataOrig = data;
+
+%put a black border around them for display purposes
+border = 5;
+bgColor = min(data(:));
+%bgColor = max(data(:));
+data = bgColor*ones(nr+2*border, nc+2*border, Nbands, Npatches, class(data));
+data(border+1:end-border, border+1:end-border, :, :) = dataOrig;
+
+[width, height, bands, nFrames] = size(data);
+
+% Determine the number of axis rows and columns.
+axCols = sqrt(nFrames);
+if (axCols<1)
+    % In case we have a slim image.
+    axCols = 1;
+end
+axRows = nFrames/axCols;
+if (ceil(axCols)-axCols) < (ceil(axRows)-axRows),
+    axCols = ceil(axCols);
+    axRows = ceil(nFrames/axCols);
+else
+    axRows = ceil(axRows); 
+    axCols = ceil(nFrames/axRows);
+end
+
+% Size the storage to hold all frames.
+storage = repmat(nativeVal, [axRows*width, axCols*height, bands, 1]);
+
+% Fill the storage up with data pixels.
+rows = 1:width; 
+cols = 1:height;
+for i=0:axRows-1,
+  for j=0:axCols-1,
+    k = j+i*axCols+1;
+    if k<=nFrames,
+      storage(rows+i*width, cols+j*height, :) = data(:,:,:,k);
+    else
+      break;
+    end
+  end
+end
+
+
+% Display the tiled frames nicely and 
+% pop the window forward.
+im = imagesc(storage);
+
+ax = get(im, 'Parent');
+fig = get(ax, 'Parent');
+set(ax, 'XTick', [], 'YTick', [])
+figure(fig)
+
+% If working with single band images, update the colormap.
+if 0 % bands==1,
+    colormap(gray);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/montageKPM3.m b/sourcecodes/bnt-master/KPMtools/montageKPM3.m
new file mode 100644
index 00000000..fb2d540a
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/montageKPM3.m
@@ -0,0 +1,5 @@
+function montageKPM3(data)
+% data{f}(y,x,b) - each frame can have a different size (can can even be empty)
+
+data2 = cell2matPad(data);
+montageKPM2(data2)
diff --git a/sourcecodes/bnt-master/KPMtools/mult_by_table.m b/sourcecodes/bnt-master/KPMtools/mult_by_table.m
new file mode 100644
index 00000000..a92e340f
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mult_by_table.m
@@ -0,0 +1,7 @@
+function bigT = mult_by_table(bigT, bigdom, bigsz, smallT, smalldom, smallsz)
+% MULT_BY_TABLE 
+% bigT = mult_by_table(bigT, bigdom, bigsz, smallT, smalldom, smallsz)
+%
+
+Ts = extend_domain_table(smallT, smalldom, smallsz, bigdom, bigsz);
+bigT(:) = bigT(:) .* Ts(:); % must have bigT(:) on LHS to preserve shape
diff --git a/sourcecodes/bnt-master/KPMtools/myintersect.m b/sourcecodes/bnt-master/KPMtools/myintersect.m
new file mode 100644
index 00000000..c1886efb
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/myintersect.m
@@ -0,0 +1,28 @@
+function C = myintersect(A,B)
+% MYINTERSECT Intersection of two sets of positive integers (much faster than built-in intersect)
+% C = myintersect(A,B)
+
+A = A(:)'; B = B(:)';
+
+if isempty(A)
+  ma = 0;
+else
+  ma = max(A);
+end
+
+if isempty(B)
+  mb = 0;
+else
+  mb = max(B);
+end
+
+if ma==0 || mb==0
+  C = [];
+else
+  %bits = sparse(1, max(ma,mb));
+  bits = zeros(1, max(ma,mb));
+  bits(A) = 1;
+  C = B(logical(bits(B)));  
+end
+
+%sum( bitget( bitand( cliquesb(i), cliquesb(j) ), 1:52 ) ); 
diff --git a/sourcecodes/bnt-master/KPMtools/myismember.m b/sourcecodes/bnt-master/KPMtools/myismember.m
new file mode 100644
index 00000000..d339bb42
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/myismember.m
@@ -0,0 +1,18 @@
+function p = myismember(a,A)
+% MYISMEMBER Is 'a' an element of a set of positive integers? (much faster than built-in ismember)
+% p = myismember(a,A)
+
+%if isempty(A) | a < min(A) | a > max(A)  % slow
+
+if length(A)==0
+  p = 0;
+elseif a < min(A)
+  p = 0;
+elseif a > max(A)
+  p = 0;
+else
+  bits = zeros(1, max(A));
+  bits(A) = 1;
+  p = bits(a);
+end
+p = logical(p);
diff --git a/sourcecodes/bnt-master/KPMtools/myismember.m~ b/sourcecodes/bnt-master/KPMtools/myismember.m~
new file mode 100644
index 00000000..6c93c11a
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/myismember.m~
@@ -0,0 +1,17 @@
+function p = myismember(a,A)
+% MYISMEMBER Is 'a' an element of a set of positive integers? (much faster than built-in ismember)
+% p = myismember(a,A)
+
+%if isempty(A) | a < min(A) | a > max(A)  % slow
+
+if length(A)==0
+  p = 0;
+elseif a < min(A)
+  p = 0;
+elseif a > max(A)
+  p = 0;
+else
+  bits = zeros(1, max(A));
+  bits(A) = 1;
+  p = bits(a);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/myones.m b/sourcecodes/bnt-master/KPMtools/myones.m
new file mode 100644
index 00000000..28d18042
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/myones.m
@@ -0,0 +1,11 @@
+function T = myones(sizes)
+% MYONES Like the built-in ones, except myones(k) produces a k*1 vector instead of a k*k matrix,
+% T = myones(sizes)
+
+if length(sizes)==0
+  T = 1;
+elseif length(sizes)==1
+  T = ones(sizes, 1);
+else
+  T = ones(sizes(:)');
+end
diff --git a/sourcecodes/bnt-master/KPMtools/myplot.m b/sourcecodes/bnt-master/KPMtools/myplot.m
new file mode 100644
index 00000000..0698e485
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/myplot.m
@@ -0,0 +1,7 @@
+colors =  ['r' 'b' 'k' 'g' 'c' 'y' 'm' ...
+	   'r' 'b' 'k' 'g' 'c' 'y' 'm'];
+symbols = ['o' 'x' 's' '>' '<' '^' 'v' ...
+	   '*' 'p' 'h' '+' 'd' 'o' 'x'];
+for i=1:length(colors)
+  styles{i} = sprintf('-%s%s', colors(i), symbols(i));
+end
diff --git a/sourcecodes/bnt-master/KPMtools/myrand.m b/sourcecodes/bnt-master/KPMtools/myrand.m
new file mode 100644
index 00000000..836b854b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/myrand.m
@@ -0,0 +1,12 @@
+function T = myrand(sizes)
+% MYRAND Like the built-in rand, except myrand(k) produces a k*1 vector instead of a k*k matrix,
+% T = myrand(sizes)
+
+if length(sizes)==0
+  warning('myrand[]');
+  T = rand(1,1);
+elseif length(sizes)==1
+  T = rand(sizes, 1);
+else
+  T = rand(sizes);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/myrepmat.m b/sourcecodes/bnt-master/KPMtools/myrepmat.m
new file mode 100644
index 00000000..830dbf41
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/myrepmat.m
@@ -0,0 +1,9 @@
+function T = myrepmat(T, sizes)
+% MYREPMAT Like the built-in repmat, except myrepmat(T,n) == repmat(T,[n 1])
+% T = myrepmat(T, sizes)
+
+if length(sizes)==1
+  T = repmat(T, [sizes 1]);
+else
+  T = repmat(T, sizes(:)');
+end
diff --git a/sourcecodes/bnt-master/KPMtools/myreshape.m b/sourcecodes/bnt-master/KPMtools/myreshape.m
new file mode 100644
index 00000000..9613f1dc
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/myreshape.m
@@ -0,0 +1,11 @@
+function T = myreshape(T, sizes)
+% MYRESHAPE Like the built-in reshape, except myreshape(T,n) == reshape(T,[n 1])
+% T = myreshape(T, sizes)
+
+if length(sizes)==0
+  return;
+elseif length(sizes)==1
+  T = reshape(T, [sizes 1]);
+else
+  T = reshape(T, sizes(:)');
+end
diff --git a/sourcecodes/bnt-master/KPMtools/mysetdiff.m b/sourcecodes/bnt-master/KPMtools/mysetdiff.m
new file mode 100644
index 00000000..fb647f4e
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mysetdiff.m
@@ -0,0 +1,19 @@
+function C = mysetdiff(A,B)
+% MYSETDIFF Set difference of two sets of positive integers (much faster than built-in setdiff)
+% C = mysetdiff(A,B)
+% C = A \ B = { things in A that are not in B }
+%
+% Original by Kevin Murphy, modified by Leon Peshkin
+
+if isempty(A)
+    C = [];
+    return;
+elseif isempty(B)
+    C = A;
+    return; 
+else % both non-empty
+    bits = zeros(1, max(max(A), max(B)));
+    bits(A) = 1;
+    bits(B) = 0;
+    C = A(logical(bits(A)));
+end
diff --git a/sourcecodes/bnt-master/KPMtools/mysize.m b/sourcecodes/bnt-master/KPMtools/mysize.m
new file mode 100644
index 00000000..40cb659c
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mysize.m
@@ -0,0 +1,16 @@
+function sz = mysize(M)
+% MYSIZE Like the built-in size, except it returns n if M is a vector of length n, and 1 if M is a scalar.
+% sz = mysize(M)
+% 
+% The behavior is best explained by examples
+% - M = rand(1,1),   mysize(M) = 1,      size(M) = [1 1]
+% - M = rand(2,1),   mysize(M) = 2,      size(M) = [2 1]
+% - M = rand(1,2),   mysize(M) = 2,      size(M) = [1 2]
+% - M = rand(2,2,1), mysize(M) = [2 2],  size(M) = [2 2]
+% - M = rand(1,2,1), mysize(M) = 2,      size(M) = [1 2]
+
+if isvectorBNT(M)
+  sz = length(M);
+else
+  sz = size(M);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/mysubset.m b/sourcecodes/bnt-master/KPMtools/mysubset.m
new file mode 100644
index 00000000..a3a2ccd2
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mysubset.m
@@ -0,0 +1,11 @@
+function p=mysubset(small,large)
+% MYSUBSET Is the small set of +ve integers a subset of the large set?
+% p = mysubset(small, large)
+
+% Surprisingly, this is not built-in.
+
+if isempty(small)
+  p = 1; % isempty(large);
+else
+  p = length(myintersect(small,large)) == length(small);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/mysymsetdiff.m b/sourcecodes/bnt-master/KPMtools/mysymsetdiff.m
new file mode 100644
index 00000000..4f143610
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/mysymsetdiff.m
@@ -0,0 +1,29 @@
+function C = mysymsetdiff(A,B)
+% MYSYMSETDIFF Symmetric set difference of two sets of positive integers (much faster than built-in setdiff)
+% C = mysetdiff(A,B)
+% C = (A\B) union (B\A) = { things that A and B don't have in common }
+
+if isempty(A)
+  ma = 0;
+else
+  ma = max(A);
+end
+
+if isempty(B)
+  mb = 0;
+else
+  mb = max(B);
+end
+
+if ma==0 
+  C = B;
+elseif mb==0
+  C = A;
+else % both non-empty
+  m = max(ma,mb);
+  bitsA = sparse(1, m);
+  bitsA(A) = 1;
+  bitsB = sparse(1, m);
+  bitsB(B) = 1;
+  C = find(xor(bitsA, bitsB));
+end
diff --git a/sourcecodes/bnt-master/KPMtools/myunion.m b/sourcecodes/bnt-master/KPMtools/myunion.m
new file mode 100644
index 00000000..0f358020
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/myunion.m
@@ -0,0 +1,29 @@
+function C = myunion(A,B)
+% MYUNION Union of two sets of positive integers (much faster than built-in union)
+% C = myunion(A,B)
+
+if isempty(A)
+  ma = 0;
+else
+  ma = max(A);
+end
+
+if isempty(B)
+  mb = 0;
+else
+  mb = max(B);
+end
+
+if ma==0 && mb==0
+  C = [];
+elseif ma==0 && mb>0
+  C = B;
+elseif ma>0 && mb==0
+  C = A;
+else
+  %bits = sparse(1, max(ma,mb));
+  bits = zeros(1, max(ma,mb));
+  bits(A) = 1;
+  bits(B) = 1;
+  C = find(bits);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/nchoose2.m b/sourcecodes/bnt-master/KPMtools/nchoose2.m
new file mode 100644
index 00000000..1827d053
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/nchoose2.m
@@ -0,0 +1,35 @@
+function c = nchoose2(v, f)
+%NCHOOSE2 All combinations of N elements taken two at a time.
+%
+%   NCHOOSE2(1:N) or NCHOOSEK(V) where V is a vector of length N,
+%   produces a matrix with N*(N-1)/2 rows and K columns. Each row of
+%   the result has K of the elements in the vector V.
+%
+%   NCHOOSE2(N,FLAG) is the same as NCHOOSE2(1:N) but faster.
+%
+%   NCHOOSE2(V) is much faster than NCHOOSEK(V,2).
+%
+%   See also NCHOOSEK, PERMS.
+
+%   Author:      Peter J. Acklam
+%   Time-stamp:  2000-03-03 13:03:59
+%   E-mail:      jacklam@math.uio.no
+%   URL:         http://www.math.uio.no/~jacklam
+
+   nargs = nargin;
+   if nargs < 1
+      error('Not enough input arguments.');
+   elseif nargs == 1
+      v = v(:);
+      n = length(v);
+   elseif nargs == 2
+      n = v;
+   else
+      error('Too many input arguments.');
+   end
+
+   [ c(:,2), c(:,1) ] = find( tril( ones(n), -1 ) );
+
+   if nargs == 1
+      c = v(c);
+   end
diff --git a/sourcecodes/bnt-master/KPMtools/ncols.m b/sourcecodes/bnt-master/KPMtools/ncols.m
new file mode 100644
index 00000000..a6fe1352
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/ncols.m
@@ -0,0 +1,4 @@
+function c = cols(x)
+% COLS    The number of columns.
+% COLS is a more readable alternative to size(x,2).
+c = size(x,2);
diff --git a/sourcecodes/bnt-master/KPMtools/nonmaxsup.m b/sourcecodes/bnt-master/KPMtools/nonmaxsup.m
new file mode 100644
index 00000000..f94d4560
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/nonmaxsup.m
@@ -0,0 +1,42 @@
+% NONMAXSUP - Non-maximal Suppression
+%
+% Usage:  cim = nonmaxsup(im, radius)
+%
+% Arguments:   
+%            im     - image to be processed.
+%            radius - radius of region considered in non-maximal
+%                     suppression (optional). Typical values to use might
+%                     be 1-3.  Default is 1.
+%
+% Returns:
+%            cim    - image with pixels that are not maximal within a 
+%                     square neighborhood zeroed out.
+
+% Copyright (C) 2002 Mark A. Paskin
+%
+% This program is free software; you can redistribute it and/or modify
+% it under the terms of the GNU General Public License as published by
+% the Free Software Foundation; either version 2 of the License, or
+% (at your option) any later version.
+%
+% This program is distributed in the hope that it will be useful, but
+% WITHOUT ANY WARRANTY; without even the implied warranty of
+% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+% General Public License for more details.
+%
+% You should have received a copy of the GNU General Public License
+% along with this program; if not, write to the Free Software
+% Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+% USA.
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+function cim = nonmaxsup(m, radius)
+  if (nargin == 1) radius = 1; end
+  % Extract local maxima by performing a grey scale morphological
+  % dilation and then finding points in the corner strength image that
+  % match the dilated image and are also greater than the threshold.
+  sze = 2 * radius + 1;                   % Size of mask.
+  mx = ordfilt2(m, sze^2, ones(sze));   % Grey-scale dilate.
+  cim = sparse(m .* (m == mx));
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/normalise.m b/sourcecodes/bnt-master/KPMtools/normalise.m
new file mode 100644
index 00000000..c6585921
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/normalise.m
@@ -0,0 +1,34 @@
+function [M, z] = normalise(A, dim)
+% NORMALISE Make the entries of a (multidimensional) array sum to 1
+% [M, c] = normalise(A)
+% c is the normalizing constant
+%
+% [M, c] = normalise(A, dim)
+% If dim is specified, we normalise the specified dimension only,
+% otherwise we normalise the whole array.
+
+if nargin < 2
+  z = sum(A(:));
+  % Set any zeros to one before dividing
+  % This is valid, since c=0 => all i. A(i)=0 => the answer should be 0/1=0
+  s = z + (z==0);
+  M = A / s;
+elseif dim==1 % normalize each column
+  z = sum(A);
+  s = z + (z==0);
+  %M = A ./ (d'*ones(1,size(A,1)))';
+  M = A ./ repmatC(s, size(A,1), 1);
+else
+  % Keith Battocchi - v. slow because of repmat
+  z=sum(A,dim);
+  s = z + (z==0);
+  L=size(A,dim);
+  d=length(size(A));
+  v=ones(d,1);
+  v(dim)=L;
+  %c=repmat(s,v);
+  c=repmat(s,v');
+  M=A./c;
+end
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/normaliseC.c b/sourcecodes/bnt-master/KPMtools/normaliseC.c
new file mode 100644
index 00000000..b0878f28
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/normaliseC.c
@@ -0,0 +1,29 @@
+/* C mex version of normalise.m in misc directory  */
+
+#include "mex.h"
+
+void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
+{
+  double *T, *sum_ptr, sum;
+  int i, N;  
+
+  plhs[0] = mxDuplicateArray(prhs[0]);
+  T = mxGetPr(plhs[0]);
+  if(mxIsSparse(plhs[0])) N = mxGetJc(plhs[0])[mxGetN(plhs[0])];
+  else N = mxGetNumberOfElements(plhs[0]);
+
+  plhs[1] = mxCreateDoubleMatrix(1, 1, mxREAL);
+  sum_ptr = mxGetPr(plhs[1]);
+
+  sum = 0;
+  for (i = 0; i < N; i++) {
+    sum += *T++;
+  }
+  T = mxGetPr(plhs[0]);
+  if (sum > 0) {
+    for (i = 0; i < N; i++) {
+      *T++ /= sum;
+    }
+  } 
+  *sum_ptr = sum;
+}
diff --git a/sourcecodes/bnt-master/KPMtools/normaliseC.dll b/sourcecodes/bnt-master/KPMtools/normaliseC.dll
new file mode 100644
index 00000000..dead3669
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/normaliseC.dll
Binary files differdiff --git a/sourcecodes/bnt-master/KPMtools/normalize.m b/sourcecodes/bnt-master/KPMtools/normalize.m
new file mode 100644
index 00000000..c6585921
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/normalize.m
@@ -0,0 +1,34 @@
+function [M, z] = normalise(A, dim)
+% NORMALISE Make the entries of a (multidimensional) array sum to 1
+% [M, c] = normalise(A)
+% c is the normalizing constant
+%
+% [M, c] = normalise(A, dim)
+% If dim is specified, we normalise the specified dimension only,
+% otherwise we normalise the whole array.
+
+if nargin < 2
+  z = sum(A(:));
+  % Set any zeros to one before dividing
+  % This is valid, since c=0 => all i. A(i)=0 => the answer should be 0/1=0
+  s = z + (z==0);
+  M = A / s;
+elseif dim==1 % normalize each column
+  z = sum(A);
+  s = z + (z==0);
+  %M = A ./ (d'*ones(1,size(A,1)))';
+  M = A ./ repmatC(s, size(A,1), 1);
+else
+  % Keith Battocchi - v. slow because of repmat
+  z=sum(A,dim);
+  s = z + (z==0);
+  L=size(A,dim);
+  d=length(size(A));
+  v=ones(d,1);
+  v(dim)=L;
+  %c=repmat(s,v);
+  c=repmat(s,v');
+  M=A./c;
+end
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/nrows.m b/sourcecodes/bnt-master/KPMtools/nrows.m
new file mode 100644
index 00000000..a8046995
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/nrows.m
@@ -0,0 +1,4 @@
+function r = rows(x)
+% ROWS      The number of rows.
+% ROWS is a more readable alternative to size(x,1).
+r = size(x,1);
diff --git a/sourcecodes/bnt-master/KPMtools/num2strcell.m b/sourcecodes/bnt-master/KPMtools/num2strcell.m
new file mode 100644
index 00000000..a63f86d4
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/num2strcell.m
@@ -0,0 +1,16 @@
+function c = num2strcell(n, format)
+% num2strcell Convert vector of numbers to cell array of strings
+% function c = num2strcell(n, format)
+%
+% If format is omitted, we use
+% c{i} = sprintf('%d', n(i))
+
+if nargin < 2, format = '%d'; end
+
+N = length(n);
+c = cell(1,N);
+for i=1:N
+  c{i} = sprintf(format, n(i));
+end
+  
+  
diff --git a/sourcecodes/bnt-master/KPMtools/optimalMatching.m b/sourcecodes/bnt-master/KPMtools/optimalMatching.m
new file mode 100644
index 00000000..a794ba02
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/optimalMatching.m
@@ -0,0 +1,90 @@
+% MATCH - Solves the weighted bipartite matching (or assignment)
+%         problem.
+%
+% Usage:  a = match(C);
+%
+% Arguments:   
+%         C     - an m x n cost matrix; the sets are taken to be
+%                 1:m and 1:n; C(i, j) gives the cost of matching
+%                 items i (of the first set) and j (of the second set)
+%
+% Returns:
+%
+%         a     - an m x 1 assignment vector, which gives the
+%                 minimum cost assignment.  a(i) is the index of
+%                 the item of 1:n that was matched to item i of
+%                 1:m.  If item i (of 1:m) was not matched to any 
+%                 item of 1:n, then a(i) is zero.
+
+% Copyright (C) 2002 Mark A. Paskin
+%
+% This program is free software; you can redistribute it and/or modify
+% it under the terms of the GNU General Public License as published by
+% the Free Software Foundation; either version 2 of the License, or
+% (at your option) any later version.
+%
+% This program is distributed in the hope that it will be useful, but
+% WITHOUT ANY WARRANTY; without even the implied warranty of
+% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+% General Public License for more details.
+%
+% You should have received a copy of the GNU General Public License
+% along with this program; if not, write to the Free Software
+% Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+% USA.
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+function [a] = optimalMatching(C)
+
+% Trivial cases:
+[p, q] = size(C);
+if (p == 0)
+  a = []; 
+  return;
+elseif (q == 0)
+  a = zeros(p, 1);
+  return;
+end
+
+
+if  0
+% First, reduce the problem by making easy optimal matches.  If two
+% elements agree that they are the best match, then match them up.
+[x, a] = min(C, [], 2);
+[y, b] = min(C, [], 1);
+u = find(1:p ~= b(a(:)));
+a(u) = 0;
+v = find(1:q ~= a(b(:))');
+C = C(u, v);
+if (isempty(C)) return; end
+end
+
+% Get the (new) size of the two sets, u and v.
+[m, n] = size(C);
+
+%mx = realmax;
+mx = 2*max(C(:));
+mn = -2*min(C(:));
+% Pad the affinity matrix to be square
+if (m < n)
+  C = [C; mx * ones(n - m, n)];
+elseif (n < m)
+  C = [C, mx * ones(m, m - n)];
+end
+
+% Run the Hungarian method.  First replace infinite values by the
+% largest (or smallest) finite values.
+C(find(isinf(C) & (C > 0))) = mx;
+C(find(isinf(C) & (C < 0))) = mn;
+%fprintf('running hungarian\n');
+[b, cost] = hungarian(C');
+
+% Extract only the real assignments
+ap = b(1:m)';
+ap(find(ap > n)) = 0;
+
+a = ap; 
+%% Incorporate this sub-assignment into the complete assignment
+%  k = find(ap);
+%  a(u(k)) = v(ap(k));
+
diff --git a/sourcecodes/bnt-master/KPMtools/optimalMatchingTest.m b/sourcecodes/bnt-master/KPMtools/optimalMatchingTest.m
new file mode 100644
index 00000000..5cb2ce4b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/optimalMatchingTest.m
@@ -0,0 +1,18 @@
+% Consider matching sources to detections
+
+%  s1 d2  
+%         s2 d3
+%  d1
+
+a  = optimalMatching([52;0.01])
+
+% sources(:,i) = [x y] coords
+sources = [0.1 0.7; 0.6 0.4]';
+detections = [0.2 0.2; 0.2 0.8; 0.7 0.1]';
+dst = sqdist(sources, detections)
+
+% a = [2 3] which means s1-d2, s2-d3
+a = optimalMatching(dst)
+
+% a = [0 1 2] which means d1-0, d2-s1, d3-s2
+a = optimalMatching(dst')
diff --git a/sourcecodes/bnt-master/KPMtools/partitionData.m b/sourcecodes/bnt-master/KPMtools/partitionData.m
new file mode 100644
index 00000000..3e5eb5fa
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/partitionData.m
@@ -0,0 +1,25 @@
+function  varargout = partitionData(Ndata, varargin)
+% PARTITIONDATA Partition a vector of indices into random sets
+% [a,b,c,...] = partitionData(N, 0.3, 0.2, 0.5, ...)
+%
+% Examples:
+% [a,b,c]=partitionData(105,0.3,0.2,0.5);
+% a= 1:30, b=32:52, c=52:105 (last bin gets all the left over)
+
+Npartitions = length(varargin);
+perm = randperm(Ndata);
+%perm = 1:Ndata;
+ndx = 1;
+for i=1:Npartitions
+  pc(i) = varargin{i};
+  Nbin(i) = fix(Ndata*pc(i));
+  low(i) = ndx;
+  if i==Npartitions
+    high(i) = Ndata;
+  else
+    high(i) = low(i)+Nbin(i)-1;
+  end
+  varargout{i} = perm(low(i):high(i));
+  ndx = ndx+Nbin(i);
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/partition_matrix_vec.m b/sourcecodes/bnt-master/KPMtools/partition_matrix_vec.m
new file mode 100644
index 00000000..6ac456c5
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/partition_matrix_vec.m
@@ -0,0 +1,21 @@
+function [m1, m2, K11, K12, K21, K22] = partition_matrix_vec(m, K, n1, n2, bs)
+% PARTITION_MATRIX_VEC Partition a vector and matrix into blocks.
+% [m1, m2, K11, K12, K21, K22] = partition_matrix_vec(m, K, blocks1, blocks2, bs)
+%
+% bs(i) = block size of i'th node
+%
+% Example:
+% n1 = [6 8], n2 = [5], bs = [- - - - 2 1 - 2], where - = don't care
+% m = [0.1 0.2   0.3   0.4 0.5], K = some 5*5 matrix,
+% So E[X5] = [0.1 0.2], E[X6] = [0.3], E[X8] = [0.4 0.5]
+% m1 = [0.3 0.4 0.5], m2 = [0.1 0.2];
+
+dom = myunion(n1, n2);
+n1i = block(find_equiv_posns(n1, dom), bs(dom));
+n2i = block(find_equiv_posns(n2, dom), bs(dom));
+m1 = m(n1i);
+m2 = m(n2i);
+K11 = K(n1i, n1i);
+K12 = K(n1i, n2i);
+K21 = K(n2i, n1i);
+K22 = K(n2i, n2i);  
diff --git a/sourcecodes/bnt-master/KPMtools/pca_kpm.m b/sourcecodes/bnt-master/KPMtools/pca_kpm.m
new file mode 100644
index 00000000..d6cbd366
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/pca_kpm.m
@@ -0,0 +1,32 @@
+function [pc_vec]=pca_kpm(features,N, method);
+% PCA_KPM Compute top N principal components using eigs or svd.
+% [pc_vec]=pca_kpm(features,N) 
+%
+% features(:,i) is the i'th example - each COLUMN is an observation
+% pc_vec(:,j) is the j'th basis function onto which you should project the data
+% using pc_vec' * features
+
+[d ncases] = size(features);
+fm=features-repmat(mean(features,2), 1, ncases);
+
+
+if method==1 % d*d < d*ncases
+  fprintf('pca_kpm eigs\n');
+  options.disp = 0;
+  C = cov(fm'); % d x d matrix
+  [pc_vec, evals] = eigs(C, N, 'LM', options);
+else 
+  % [U,D,V] = SVD(fm), U(:,i)=evec of fm fm', V(:,i) = evec of fm' fm
+  fprintf('pca_kpm svds\n');
+  [U,D,V] = svds(fm', N);
+  pc_vec = V;
+end
+
+if 0
+X = randn(5,3);
+X = X-repmat(mean(X),5,1);
+C = X'*X;
+C2=cov(X)
+[U,D,V]=svd(X);
+[V2,D2]=eig(X)
+end
diff --git a/sourcecodes/bnt-master/KPMtools/pca_netlab.m b/sourcecodes/bnt-master/KPMtools/pca_netlab.m
new file mode 100644
index 00000000..4b7063d6
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/pca_netlab.m
@@ -0,0 +1,42 @@
+function [PCcoeff, PCvec] = pca(data, N)
+%PCA	Principal Components Analysis
+%
+%	Description
+%	 PCCOEFF = PCA(DATA) computes the eigenvalues of the covariance
+%	matrix of the dataset DATA and returns them as PCCOEFF.  These
+%	coefficients give the variance of DATA along the corresponding
+%	principal components.
+%
+%	PCCOEFF = PCA(DATA, N) returns the largest N eigenvalues.
+%
+%	[PCCOEFF, PCVEC] = PCA(DATA) returns the principal components as well
+%	as the coefficients.  This is considerably more computationally
+%	demanding than just computing the eigenvalues.
+%
+%	See also
+%	EIGDEC, GTMINIT, PPCA
+%
+
+%	Copyright (c) Ian T Nabney (1996-2001)
+
+if nargin == 1
+   N = size(data, 2);
+end
+
+if nargout == 1
+   evals_only = logical(1);
+else
+   evals_only = logical(0);
+end
+
+if N ~= round(N) | N < 1 | N > size(data, 2)
+   error('Number of PCs must be integer, >0, < dim');
+end
+
+% Find the sorted eigenvalues of the data covariance matrix
+if evals_only
+   PCcoeff = eigdec(cov(data), N);
+else
+  [PCcoeff, PCvec] = eigdec(cov(data), N);
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/pick.m b/sourcecodes/bnt-master/KPMtools/pick.m
new file mode 100644
index 00000000..8e40d937
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/pick.m
@@ -0,0 +1,9 @@
+function [i,j] = pick(ndx)
+% PICK Pick an entry at random from a vector
+% function [i,j] = pick(ndx)
+%
+% i = ndx(j) for j ~ U(1:length(ndx))
+
+dist = normalize(ones(1,length(ndx)));
+j = sample_discrete(dist);
+i = ndx(j);
diff --git a/sourcecodes/bnt-master/KPMtools/plotBox.m b/sourcecodes/bnt-master/KPMtools/plotBox.m
new file mode 100644
index 00000000..fb057c33
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plotBox.m
@@ -0,0 +1,22 @@
+function [h, ht] =plotBox(box, col, str)
+% function h=plotBox(box, col, str)
+%
+% box = [xlow xhigh ylow yhigh]
+% col = color (default - red)
+% str = string printed at center (default '')
+
+if nargin < 2, col = 'r'; end
+if nargin < 3, str = ''; end
+
+box = double(box); % fails on single
+
+h = plot([box(1) box(2) box(2) box(1) box(1)], [ box(3) box(3) box(4) box(4) box(3)]);
+set(h, 'color', col);
+set(h, 'linewidth', 2);
+if ~isempty(str)
+  xc = mean(box(1:2));
+  yc = mean(box(3:4));
+  ht = text(xc, yc, str);
+else
+  ht = [];
+end
diff --git a/sourcecodes/bnt-master/KPMtools/plotColors.m b/sourcecodes/bnt-master/KPMtools/plotColors.m
new file mode 100644
index 00000000..ded97483
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plotColors.m
@@ -0,0 +1,10 @@
+function styles =  plotColors()
+
+colors =  ['r' 'b' 'k' 'g' 'c' 'y' 'm' ...
+	   'r' 'b' 'k' 'g' 'c' 'y' 'm'];
+symbols = ['o' 'x' '+' '>' '<' '^' 'v' ...
+	   '*' 'p' 'h' 's' 'd' 'o' 'x'];
+for i=1:length(colors)
+  styles{i} = sprintf('-%s%s', colors(i), symbols(i));
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/plotROC.m b/sourcecodes/bnt-master/KPMtools/plotROC.m
new file mode 100644
index 00000000..4c3de06e
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plotROC.m
@@ -0,0 +1,26 @@
+function [falseAlarmRate, detectionRate, area, th] = plotROC(confidence, testClass, col, varargin)
+% function [falseAlarmRate, detectionRate, area, th] = plotroc(confidence, testClass, color)
+
+if nargin < 3, col = []; end
+
+[scale01] = process_options(varargin, 'scale01', 1);
+
+[falseAlarmRate detectionRate area th] = computeROC(confidence, testClass);
+
+if ~isempty(col)
+    h=plot(falseAlarmRate, detectionRate, [col '-']);
+    %set(h, 'linewidth', 2);
+    ex = 0.05*max(falseAlarmRate);
+    ey = 0.05;
+    if scale01
+      axis([0-ex max(falseAlarmRate)+ex 0-ey 1+ey])
+    else
+      % zoom in on the top left corner
+      axis([0-ex max(falseAlarmRate)*0.5+ex 0.5-ey 1+ey])
+    end
+    grid on
+    ylabel('detection rate')
+    %xlabel('# false alarms')
+    xlabel('false alarm rate')
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/plotROCkpm.m b/sourcecodes/bnt-master/KPMtools/plotROCkpm.m
new file mode 100644
index 00000000..a77fd568
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plotROCkpm.m
@@ -0,0 +1,69 @@
+function [falseAlarmRate, detectionRate, area, th] = plotROC(confidence, testClass, col, varargin)
+% You pass the scores and the classes, and the function returns the false
+% alarm rate and the detection rate for different points across the ROC.
+%
+% [faR, dR] = plotROC(score, class)
+%
+%  faR (false alarm rate) is uniformly sampled from 0 to 1
+%  dR (detection rate) is computed using the scores.
+%
+% class = 0 => target absent
+% class = 1 => target present
+%
+% score is the output of the detector, or any other measure of detection.
+% There is no plot unless you add a third parameter that is the color of
+% the graph. For instance:
+% [faR, dR] = plotROC(score, class, 'r')
+%
+% faR, dR are size 1x1250
+
+if nargin < 3, col = []; end
+[scale01] = process_options(varargin, 'scale01', 1);
+
+S = rand('state');
+rand('state',0);
+confidence = confidence + rand(size(confidence))*10^(-10);
+rand('state',S)
+
+ndxAbs = find(testClass==0); % absent
+ndxPres = find(testClass==1); % present
+
+[th, j] = sort(confidence(ndxAbs));
+th = th(fix(linspace(1, length(th), 1250))); 
+
+cAbs = confidence(ndxAbs);
+cPres = confidence(ndxPres);
+for t=1:length(th)
+  if length(ndxPres) == 0
+    detectionRate(t) = 0;
+  else
+    detectionRate(t)  = sum(cPres>=th(t)) / length(ndxPres);
+  end
+  if length(ndxAbs) == 0
+    falseAlarmRate(t) = 0;
+  else
+    falseAlarmRate(t) = sum(cAbs>=th(t)) / length(ndxAbs);
+  end
+  
+  %detectionRate(t)  = sum(confidence(ndxPres)>=th(t)) / length(ndxPres);
+  %falseAlarmRate(t) = sum(confidence(ndxAbs)>=th(t)) / length(ndxAbs);
+  %detections(t)     = sum(confidence(ndxPres)>=th(t));
+  %falseAlarms(t)    = sum(confidence(ndxAbs)>=th(t));
+end
+
+area = sum(abs(falseAlarmRate(2:end) - falseAlarmRate(1:end-1)) .* detectionRate(2:end));
+
+if ~isempty(col)
+    h=plot(falseAlarmRate, detectionRate, [col '-']);
+    %set(h, 'linewidth', 2);
+    e = 0.05;
+    if scale01
+      axis([0-e 1+e 0-e 1+e])
+    else
+      % zoom in on the top left corner
+      axis([0-e 0.5+e 0.5-e 1+e])
+    end
+    grid on
+    ylabel('detection rate')
+    xlabel('false alarm rate')
+end
diff --git a/sourcecodes/bnt-master/KPMtools/plot_axis_thru_origin.m b/sourcecodes/bnt-master/KPMtools/plot_axis_thru_origin.m
new file mode 100644
index 00000000..353376e4
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plot_axis_thru_origin.m
@@ -0,0 +1,3 @@
+function plot_axis_thru_origin()
+
+lnx=line(get(gca,'xlim'),[0 0]); lny=line([0 0],get(gca,'ylim'));
diff --git a/sourcecodes/bnt-master/KPMtools/plot_ellipse.m b/sourcecodes/bnt-master/KPMtools/plot_ellipse.m
new file mode 100644
index 00000000..e101a158
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plot_ellipse.m
@@ -0,0 +1,19 @@
+% PLOT_ELLIPSE
+% h=plot_ellipse(x,y,theta,a,b)
+%
+% This routine plots an ellipse with centre (x,y), axis lengths a,b
+% with major axis at an angle of theta radians from the horizontal.
+
+%
+% Author: P. Fieguth
+%         Jan. 98
+%
+%http://ocho.uwaterloo.ca/~pfieguth/Teaching/372/plot_ellipse.m
+
+function h=plot_ellipse(x,y,theta,a,b)
+
+np = 100;
+ang = [0:np]*2*pi/np;
+R = [cos(theta) -sin(theta); sin(theta) cos(theta)];
+pts = [x;y]*ones(size(ang)) + R*[cos(ang)*a; sin(ang)*b];
+h=plot( pts(1,:), pts(2,:) );
diff --git a/sourcecodes/bnt-master/KPMtools/plot_matrix.m b/sourcecodes/bnt-master/KPMtools/plot_matrix.m
new file mode 100644
index 00000000..58a9a964
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plot_matrix.m
@@ -0,0 +1,48 @@
+function plot_matrix(G, bw)
+% PLOT_MATRIX Plot a 2D matrix as a grayscale image, and label the axes
+%
+% plot_matrix(M)
+%
+% For 0/1 matrices (eg. adjacency matrices), use
+% plot_matrix(M,1)
+
+if nargin < 2, bw = 0; end
+
+if 0
+  imagesc(G)
+  %image(G)
+  %colormap([1 1 1; 0 0 0]); % black squares on white background
+  %colormap(gray)
+  grid on
+  n = length(G);
+  
+  % shift the grid lines so they don't intersect the squares
+  set(gca,'xtick',1.5:1:n);
+  set(gca,'ytick',1.5:1:n);
+  
+  % Turn off the confusing labels, which are fractional
+  % Ideally we could shift the labels to lie between the axis lines...
+%  set(gca,'xticklabel', []);
+%  set(gca,'yticklabel', []);
+else
+  % solution provided by Jordan Rosenthal <jr@ece.gatech.edu>
+  % You can plot the grid lines manually:
+  % This uses the trick that a point with a value nan does not get plotted.
+  imagesc(G);
+  if bw
+    colormap([1 1 1; 0 0 0]);
+  end
+  n = length(G);
+  x = 1.5:1:n;
+  x = [ x; x; repmat(nan,1,n-1) ];
+  y = [ 0.5 n+0.5 nan ].';
+  y = repmat(y,1,n-1);
+  x = x(:);
+  y = y(:);
+  line(x,y,'linestyle',':','color','k');
+  line(y,x,'linestyle',':','color','k');
+  set(gca,'xtick',1:n)
+  set(gca,'ytick',1:n)
+end
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/plot_polygon.m b/sourcecodes/bnt-master/KPMtools/plot_polygon.m
new file mode 100644
index 00000000..d5aa1e19
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plot_polygon.m
@@ -0,0 +1,23 @@
+function out=plot_polygon(p, args, close_loop)
+% PLOT_POLYGON
+% function handle=plot_polygon(p, args, close_loop)
+% p(1,i), p(2,i) are the x/y coords of point i.
+% If non-empty, args are passed thru to the plot command.
+% If close_loop = 1, connect the last point to the first 
+
+% All rights reserved. Documentation updated April 1999.
+% Matt Kawski. http://math.la.asu.edu/~kawski
+% He calls it pplot
+
+if nargin < 2, args = []; end
+if nargin < 3, close_loop = 0; end
+
+if close_loop
+  p = [p p(:,1)];
+end
+
+if isempty(args)
+   out=plot(p(1,:),p(2,:));
+else   
+   out=plot(p(1,:),p(2,:),args);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/plotcov2.m b/sourcecodes/bnt-master/KPMtools/plotcov2.m
new file mode 100644
index 00000000..b42c8c1b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plotcov2.m
@@ -0,0 +1,86 @@
+% PLOTCOV2 - Plots a covariance ellipse with major and minor axes
+%            for a bivariate Gaussian distribution.
+%
+% Usage:
+%   h = plotcov2(mu, Sigma[, OPTIONS]);
+% 
+% Inputs:
+%   mu    - a 2 x 1 vector giving the mean of the distribution.
+%   Sigma - a 2 x 2 symmetric positive semi-definite matrix giving
+%           the covariance of the distribution (or the zero matrix).
+%
+% Options:
+%   'conf'    - a scalar between 0 and 1 giving the confidence
+%               interval (i.e., the fraction of probability mass to
+%               be enclosed by the ellipse); default is 0.9.
+%   'num-pts' - the number of points to be used to plot the
+%               ellipse; default is 100.
+%
+% This function also accepts options for PLOT.
+%
+% Outputs:
+%   h     - a vector of figure handles to the ellipse boundary and
+%           its major and minor axes
+%
+% See also: PLOTCOV3
+
+% Copyright (C) 2002 Mark A. Paskin
+%
+% This program is free software; you can redistribute it and/or modify
+% it under the terms of the GNU General Public License as published by
+% the Free Software Foundation; either version 2 of the License, or
+% (at your option) any later version.
+%
+% This program is distributed in the hope that it will be useful, but
+% WITHOUT ANY WARRANTY; without even the implied warranty of
+% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+% General Public License for more details.
+%
+% You should have received a copy of the GNU General Public License
+% along with this program; if not, write to the Free Software
+% Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+% USA.
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+function h = plotcov2(mu, Sigma, varargin)
+
+if size(Sigma) ~= [2 2], error('Sigma must be a 2 by 2 matrix'); end
+if length(mu) ~= 2, error('mu must be a 2 by 1 vector'); end
+
+[p, ...
+ n, ...
+ plot_opts] = process_options(varargin, 'conf', 0.9, ...
+					'num-pts', 100);
+h = [];
+holding = ishold;
+if (Sigma == zeros(2, 2))
+  z = mu;
+else
+  % Compute the Mahalanobis radius of the ellipsoid that encloses
+  % the desired probability mass.
+  k = conf2mahal(p, 2);
+  % The major and minor axes of the covariance ellipse are given by
+  % the eigenvectors of the covariance matrix.  Their lengths (for
+  % the ellipse with unit Mahalanobis radius) are given by the
+  % square roots of the corresponding eigenvalues.
+  if (issparse(Sigma))
+    [V, D] = eigs(Sigma);
+  else
+    [V, D] = eig(Sigma);
+  end
+  % Compute the points on the surface of the ellipse.
+  t = linspace(0, 2*pi, n);
+  u = [cos(t); sin(t)];
+  w = (k * V * sqrt(D)) * u;
+  z = repmat(mu, [1 n]) + w;
+  % Plot the major and minor axes.
+  L = k * sqrt(diag(D));
+  h = plot([mu(1); mu(1) + L(1) * V(1, 1)], ...
+	   [mu(2); mu(2) + L(1) * V(2, 1)], plot_opts{:});
+  hold on;
+  h = [h; plot([mu(1); mu(1) + L(2) * V(1, 2)], ...
+	       [mu(2); mu(2) + L(2) * V(2, 2)], plot_opts{:})];
+end
+
+h = [h; plot(z(1, :), z(2, :), plot_opts{:})];
+if (~holding) hold off; end
diff --git a/sourcecodes/bnt-master/KPMtools/plotcov2New.m b/sourcecodes/bnt-master/KPMtools/plotcov2New.m
new file mode 100644
index 00000000..ec5554bb
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plotcov2New.m
@@ -0,0 +1,119 @@
+% PLOTCOV2 - Plots a covariance ellipsoid with axes for a bivariate
+%            Gaussian distribution.
+%
+% Usage:
+%   [h, s] = plotcov2(mu, Sigma[, OPTIONS]);
+% 
+% Inputs:
+%   mu    - a 2 x 1 vector giving the mean of the distribution.
+%   Sigma - a 2 x 2 symmetric positive semi-definite matrix giving
+%           the covariance of the distribution (or the zero matrix).
+%
+% Options:
+%   'conf'      - a scalar between 0 and 1 giving the confidence
+%                 interval (i.e., the fraction of probability mass to
+%                 be enclosed by the ellipse); default is 0.9.
+%   'num-pts'   - if the value supplied is n, then (n + 1)^2 points
+%                 to be used to plot the ellipse; default is 20.
+%   'label'     - if non-empty, a string that will label the
+%                 ellipsoid (default: [])
+%   'plot-axes' - a 0/1 flag indicating if the ellipsoid's axes
+%                 should be plotted (default: 1)
+%   'plot-opts' - a cell vector of arguments to be handed to PLOT3
+%                 to contol the appearance of the axes, e.g., 
+%                 {'Color', 'g', 'LineWidth', 1}; the default is {}
+%   'fill-color' - a color specifier; is this is not [], the
+%                  covariance ellipse is filled with this color
+%                  (default: [])
+% 
+% Outputs:
+%   h     - a vector of handles on the axis lines
+%
+% See also: PLOTCOV3
+
+% Copyright (C) 2002 Mark A. Paskin
+%
+% This program is free software; you can redistribute it and/or modify
+% it under the terms of the GNU General Public License as published by
+% the Free Software Foundation; either version 2 of the License, or
+% (at your option) any later version.
+%
+% This program is distributed in the hope that it will be useful, but
+% WITHOUT ANY WARRANTY; without even the implied warranty of
+% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+% General Public License for more details.
+%
+% You should have received a copy of the GNU General Public License
+% along with this program; if not, write to the Free Software
+% Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+% USA.
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+function [h, s] = plotcov2New(mu, Sigma, varargin)
+
+h = [];
+s = [];
+
+if size(Sigma) ~= [2 2], error('Sigma must be a 2 by 2 matrix'); end
+if length(mu) ~= 2, error('mu must be a 2 by 1 vector'); end
+
+Sigma = checkpsd(Sigma);
+
+[p, ...
+ n, ...
+ label, ...
+ plot_axes, ...
+ plot_opts, ...
+ fill_color] = process_options(varargin, 'conf', 0.9, ...
+			       'num-pts', 20, ...
+			       'label', [], ...
+			       'plot-axes', 1, ...
+			       'plot-opts', {}, ...
+			       'fill-color', []);
+holding = ishold;
+% Compute the Mahalanobis radius of the ellipsoid that encloses
+% the desired probability mass.
+k = conf2mahal(p, 2);
+% Scale the covariance matrix so the confidence region has unit
+% Mahalanobis distance.
+Sigma = Sigma * k;
+% The axes of the covariance ellipse are given by the eigenvectors of
+% the covariance matrix.  Their lengths (for the ellipse with unit
+% Mahalanobis radius) are given by the square roots of the
+% corresponding eigenvalues.
+[V, D] = eig(full(Sigma));
+V = real(V);
+D = real(D);
+D = abs(D);
+
+% Compute the points on the boundary of the ellipsoid.
+t = linspace(0, 2*pi, n);
+u = [cos(t(:))'; sin(t(:))'];
+w = (V * sqrt(D)) * u;
+z = repmat(mu(:), [1 n]) + w;
+h = [h; plot(z(1, :), z(2, :), plot_opts{:})];
+if (~isempty(fill_color))
+  s = patch(z(1, :), z(2, :), fill_color);
+end
+
+% Plot the axes.
+if (plot_axes)
+  hold on;
+  L = sqrt(diag(D));
+  h = plot([mu(1); mu(1) + L(1) * V(1, 1)], ...
+	   [mu(2); mu(2) + L(1) * V(2, 1)], plot_opts{:});
+  h = [h; plot([mu(1); mu(1) + L(2) * V(1, 2)], ...
+	       [mu(2); mu(2) + L(2) * V(2, 2)], plot_opts{:})];
+end
+
+
+if (~isempty(label))
+  th = text(mu(1), mu(2), label);
+  set(th, 'FontSize', 18);
+  set(th, 'FontName', 'Times');
+  set(th, 'FontWeight', 'bold');
+  set(th, 'FontAngle', 'italic');
+  set(th, 'HorizontalAlignment', 'center');
+end
+
+if (~holding & plot_axes) hold off; end
diff --git a/sourcecodes/bnt-master/KPMtools/plotcov3.m b/sourcecodes/bnt-master/KPMtools/plotcov3.m
new file mode 100644
index 00000000..bacdcb27
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plotcov3.m
@@ -0,0 +1,109 @@
+% PLOTCOV3 - Plots a covariance ellipsoid with axes for a trivariate
+%            Gaussian distribution.
+%
+% Usage:
+%   [h, s] = plotcov3(mu, Sigma[, OPTIONS]);
+% 
+% Inputs:
+%   mu    - a 3 x 1 vector giving the mean of the distribution.
+%   Sigma - a 3 x 3 symmetric positive semi-definite matrix giving
+%           the covariance of the distribution (or the zero matrix).
+%
+% Options:
+%   'conf'      - a scalar between 0 and 1 giving the confidence
+%                 interval (i.e., the fraction of probability mass to
+%                 be enclosed by the ellipse); default is 0.9.
+%   'num-pts'   - if the value supplied is n, then (n + 1)^2 points
+%                 to be used to plot the ellipse; default is 20.
+%   'plot-opts' - a cell vector of arguments to be handed to PLOT3
+%                 to contol the appearance of the axes, e.g., 
+%                 {'Color', 'g', 'LineWidth', 1}; the default is {}
+%   'surf-opts' - a cell vector of arguments to be handed to SURF
+%                 to contol the appearance of the ellipsoid
+%                 surface; a nice possibility that yields
+%                 transparency is: {'EdgeAlpha', 0, 'FaceAlpha',
+%                 0.1, 'FaceColor', 'g'}; the default is {}
+% 
+% Outputs:
+%   h     - a vector of handles on the axis lines
+%   s     - a handle on the ellipsoid surface object
+%
+% See also: PLOTCOV2
+
+% Copyright (C) 2002 Mark A. Paskin
+%
+% This program is free software; you can redistribute it and/or modify
+% it under the terms of the GNU General Public License as published by
+% the Free Software Foundation; either version 2 of the License, or
+% (at your option) any later version.
+%
+% This program is distributed in the hope that it will be useful, but
+% WITHOUT ANY WARRANTY; without even the implied warranty of
+% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+% General Public License for more details.
+%
+% You should have received a copy of the GNU General Public License
+% along with this program; if not, write to the Free Software
+% Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+% USA.
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+function [h, s] = plotcov3(mu, Sigma, varargin)
+
+if size(Sigma) ~= [3 3], error('Sigma must be a 3 by 3 matrix'); end
+if length(mu) ~= 3, error('mu must be a 3 by 1 vector'); end
+
+[p, ...
+ n, ...
+ plot_opts, ...
+ surf_opts] = process_options(varargin, 'conf', 0.9, ...
+					'num-pts', 20, ...
+			                'plot-opts', {}, ...
+			                'surf-opts', {});
+h = [];
+holding = ishold;
+if (Sigma == zeros(3, 3))
+  z = mu;
+else
+  % Compute the Mahalanobis radius of the ellipsoid that encloses
+  % the desired probability mass.
+  k = conf2mahal(p, 3);
+  % The axes of the covariance ellipse are given by the eigenvectors of
+  % the covariance matrix.  Their lengths (for the ellipse with unit
+  % Mahalanobis radius) are given by the square roots of the
+  % corresponding eigenvalues.
+  if (issparse(Sigma))
+    [V, D] = eigs(Sigma);
+  else
+    [V, D] = eig(Sigma);
+  end
+  if (any(diag(D) < 0))
+    error('Invalid covariance matrix: not positive semi-definite.');
+  end
+  % Compute the points on the surface of the ellipsoid.
+  t = linspace(0, 2*pi, n);
+  [X, Y, Z] = sphere(n);
+  u = [X(:)'; Y(:)'; Z(:)'];
+  w = (k * V * sqrt(D)) * u;
+  z = repmat(mu(:), [1 (n + 1)^2]) + w;
+
+  % Plot the axes.
+  L = k * sqrt(diag(D));
+  h = plot3([mu(1); mu(1) + L(1) * V(1, 1)], ...
+	    [mu(2); mu(2) + L(1) * V(2, 1)], ...
+	    [mu(3); mu(3) + L(1) * V(3, 1)], plot_opts{:});
+  hold on;
+  h = [h; plot3([mu(1); mu(1) + L(2) * V(1, 2)], ...
+		[mu(2); mu(2) + L(2) * V(2, 2)], ...
+		[mu(3); mu(3) + L(2) * V(3, 2)], plot_opts{:})];
+  h = [h; plot3([mu(1); mu(1) + L(3) * V(1, 3)], ...
+		[mu(2); mu(2) + L(3) * V(2, 3)], ...
+		[mu(3); mu(3) + L(3) * V(3, 3)], plot_opts{:})];
+end
+
+s = surf(reshape(z(1, :), [(n + 1) (n + 1)]), ...
+	 reshape(z(2, :), [(n + 1) (n + 1)]), ...
+	 reshape(z(3, :), [(n + 1) (n + 1)]), ...
+	 surf_opts{:});
+
+if (~holding) hold off; end
diff --git a/sourcecodes/bnt-master/KPMtools/plotgauss1d.m b/sourcecodes/bnt-master/KPMtools/plotgauss1d.m
new file mode 100644
index 00000000..b20da3c1
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plotgauss1d.m
@@ -0,0 +1,9 @@
+function h = plotgauss1d(mu, sigma2)
+% function h = plotgauss1d(mu, sigma^2)
+% Example
+% plotgauss1d(0,5); hold on; h=plotgauss1d(0,2);set(h,'color','r')
+
+sigma = sqrt(sigma2);
+x = linspace(mu-3*sigma, mu+3*sigma, 100);
+p = gaussian_prob(x, mu, sigma2);
+h = plot(x, p, '-');
diff --git a/sourcecodes/bnt-master/KPMtools/plotgauss2d.m b/sourcecodes/bnt-master/KPMtools/plotgauss2d.m
new file mode 100644
index 00000000..a507b258
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plotgauss2d.m
@@ -0,0 +1,130 @@
+function h=plotgauss2d(mu, Sigma)
+% PLOTGAUSS2D Plot a 2D Gaussian as an ellipse with optional cross hairs
+% h=plotgauss2(mu, Sigma)
+%
+
+h = plotcov2(mu, Sigma);
+return;
+
+%%%%%%%%%%%%%%%%%%%%%%%%
+
+% PLOTCOV2 - Plots a covariance ellipse with major and minor axes
+%            for a bivariate Gaussian distribution.
+%
+% Usage:
+%   h = plotcov2(mu, Sigma[, OPTIONS]);
+% 
+% Inputs:
+%   mu    - a 2 x 1 vector giving the mean of the distribution.
+%   Sigma - a 2 x 2 symmetric positive semi-definite matrix giving
+%           the covariance of the distribution (or the zero matrix).
+%
+% Options:
+%   'conf'    - a scalar between 0 and 1 giving the confidence
+%               interval (i.e., the fraction of probability mass to
+%               be enclosed by the ellipse); default is 0.9.
+%   'num-pts' - the number of points to be used to plot the
+%               ellipse; default is 100.
+%
+% This function also accepts options for PLOT.
+%
+% Outputs:
+%   h     - a vector of figure handles to the ellipse boundary and
+%           its major and minor axes
+%
+% See also: PLOTCOV3
+
+% Copyright (C) 2002 Mark A. Paskin
+
+function h = plotcov2(mu, Sigma, varargin)
+
+if size(Sigma) ~= [2 2], error('Sigma must be a 2 by 2 matrix'); end
+if length(mu) ~= 2, error('mu must be a 2 by 1 vector'); end
+
+[p, ...
+ n, ...
+ plot_opts] = process_options(varargin, 'conf', 0.9, ...
+					'num-pts', 100);
+h = [];
+holding = ishold;
+if (Sigma == zeros(2, 2))
+  z = mu;
+else
+  % Compute the Mahalanobis radius of the ellipsoid that encloses
+  % the desired probability mass.
+  k = conf2mahal(p, 2);
+  % The major and minor axes of the covariance ellipse are given by
+  % the eigenvectors of the covariance matrix.  Their lengths (for
+  % the ellipse with unit Mahalanobis radius) are given by the
+  % square roots of the corresponding eigenvalues.
+  if (issparse(Sigma))
+    [V, D] = eigs(Sigma);
+  else
+    [V, D] = eig(Sigma);
+  end
+  % Compute the points on the surface of the ellipse.
+  t = linspace(0, 2*pi, n);
+  u = [cos(t); sin(t)];
+  w = (k * V * sqrt(D)) * u;
+  z = repmat(mu, [1 n]) + w;
+  % Plot the major and minor axes.
+  L = k * sqrt(diag(D));
+  h = plot([mu(1); mu(1) + L(1) * V(1, 1)], ...
+	   [mu(2); mu(2) + L(1) * V(2, 1)], plot_opts{:});
+  hold on;
+  h = [h; plot([mu(1); mu(1) + L(2) * V(1, 2)], ...
+	       [mu(2); mu(2) + L(2) * V(2, 2)], plot_opts{:})];
+end
+
+h = [h; plot(z(1, :), z(2, :), plot_opts{:})];
+if (~holding) hold off; end
+
+%%%%%%%%%%%%
+
+% CONF2MAHAL - Translates a confidence interval to a Mahalanobis
+%              distance.  Consider a multivariate Gaussian
+%              distribution of the form
+%
+%   p(x) = 1/sqrt((2 * pi)^d * det(C)) * exp((-1/2) * MD(x, m, inv(C)))
+%
+%              where MD(x, m, P) is the Mahalanobis distance from x
+%              to m under P:
+%
+%                 MD(x, m, P) = (x - m) * P * (x - m)'
+%
+%              A particular Mahalanobis distance k identifies an
+%              ellipsoid centered at the mean of the distribution.
+%              The confidence interval associated with this ellipsoid
+%              is the probability mass enclosed by it.  Similarly,
+%              a particular confidence interval uniquely determines
+%              an ellipsoid with a fixed Mahalanobis distance.
+%
+%              If X is an d dimensional Gaussian-distributed vector,
+%              then the Mahalanobis distance of X is distributed
+%              according to the Chi-squared distribution with d
+%              degrees of freedom.  Thus, the Mahalanobis distance is
+%              determined by evaluating the inverse cumulative
+%              distribution function of the chi squared distribution
+%              up to the confidence value.
+%
+% Usage:
+% 
+%   m = conf2mahal(c, d);
+%
+% Inputs:
+%
+%   c    - the confidence interval
+%   d    - the number of dimensions of the Gaussian distribution
+%
+% Outputs:
+%
+%   m    - the Mahalanobis radius of the ellipsoid enclosing the
+%          fraction c of the distribution's probability mass
+%
+% See also: MAHAL2CONF
+
+% Copyright (C) 2002 Mark A. Paskin
+
+function m = conf2mahal(c, d)
+
+m = chi2inv(c, d); % matlab stats toolbox
diff --git a/sourcecodes/bnt-master/KPMtools/plotgauss2d_old.m b/sourcecodes/bnt-master/KPMtools/plotgauss2d_old.m
new file mode 100644
index 00000000..08d1d14d
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/plotgauss2d_old.m
@@ -0,0 +1,40 @@
+function h=plotgauss2d_old(mu, Sigma, plot_cross)
+% PLOTGAUSS2D Plot a 2D Gaussian as an ellipse with optional cross hairs
+% h=plotgauss2(mu, Sigma)
+% 
+% h=plotgauss2(mu, Sigma, 1) also plots the major and minor axes
+%
+% Example
+% clf; S=[2 1; 1 2]; plotgauss2d([0;0], S, 1); axis equal
+
+if nargin < 3, plot_cross = 0; end
+[V,D]=eig(Sigma);
+lam1 = D(1,1);
+lam2 = D(2,2);
+v1 = V(:,1);
+v2 = V(:,2);
+%assert(approxeq(v1' * v2, 0))
+if v1(1)==0
+  theta = 0; % horizontal
+else
+  theta = atan(v1(2)/v1(1));
+end
+a = sqrt(lam1);
+b = sqrt(lam2);
+h=plot_ellipse(mu(1), mu(2), theta, a,b);
+
+if plot_cross
+  mu = mu(:);
+  held = ishold;
+  hold on
+  minor1 = mu-a*v1; minor2 = mu+a*v1;
+  hminor = line([minor1(1) minor2(1)], [minor1(2) minor2(2)]);
+  
+  major1 = mu-b*v2; major2 = mu+b*v2;
+  hmajor = line([major1(1) major2(1)], [major1(2) major2(2)]);
+  %set(hmajor,'color','r')
+  if ~held
+    hold off
+  end
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/polygon_area.m b/sourcecodes/bnt-master/KPMtools/polygon_area.m
new file mode 100644
index 00000000..43dffc77
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/polygon_area.m
@@ -0,0 +1,22 @@
+function  a = polygon_area(x,y)
+% AREA  Area of a planar polygon.
+%	AREA(X,Y) Calculates the area of a 2-dimensional
+%	polygon formed by vertices with coordinate vectors
+%	X and Y. The result is direction-sensitive: the
+%	area is positive if the bounding contour is counter-
+%	clockwise and negative if it is clockwise.
+%
+%	See also TRAPZ.
+
+%  Copyright (c) 1995 by Kirill K. Pankratov,
+%	kirill@plume.mit.edu.
+%	04/20/94, 05/20/95  
+
+ % Make polygon closed .............
+x = [x(:); x(1)];
+y = [y(:); y(1)];
+
+ % Calculate contour integral Int -y*dx  (same as Int x*dy).
+lx = length(x);
+a = -(x(2:lx)-x(1:lx-1))'*(y(1:lx-1)+y(2:lx))/2;
+a = abs(a);
diff --git a/sourcecodes/bnt-master/KPMtools/polygon_centroid.m b/sourcecodes/bnt-master/KPMtools/polygon_centroid.m
new file mode 100644
index 00000000..f3e3947f
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/polygon_centroid.m
@@ -0,0 +1,79 @@
+function [x0,y0] = centroid(x,y)
+% CENTROID Center of mass of a polygon.
+%	[X0,Y0] = CENTROID(X,Y) Calculates centroid 
+%	(center of mass) of planar polygon with vertices 
+%	coordinates X, Y.
+%	Z0 = CENTROID(X+i*Y) returns Z0=X0+i*Y0 the same
+%	as CENTROID(X,Y).
+
+%  Copyright (c) 1995 by Kirill K. Pankratov,
+%       kirill@plume.mit.edu.
+%       06/01/95, 06/07/95
+
+% Algorithm:
+%  X0 = Int{x*ds}/Int{ds}, where ds - area element
+%  so that Int{ds} is total area of a polygon.
+%    Using Green's theorem the area integral can be 
+%  reduced to a contour integral:
+%  Int{x*ds} = -Int{x^2*dy}, Int{ds} = Int{x*dy} along
+%  the perimeter of a polygon.
+%    For a polygon as a sequence of line segments
+%  this can be reduced exactly to a sum:
+%  Int{x^2*dy} = Sum{ (x_{i}^2+x_{i+1}^2+x_{i}*x_{i+1})*
+%  (y_{i+1}-y_{i})}/3;
+%  Int{x*dy} = Sum{(x_{i}+x_{i+1})(y_{i+1}-y_{i})}/2.
+%    Similarly
+%  Y0 = Int{y*ds}/Int{ds}, where
+%  Int{y*ds} = Int{y^2*dx} = 
+%  = Sum{ (y_{i}^2+y_{i+1}^2+y_{i}*y_{i+1})*
+%  (x_{i+1}-x_{i})}/3.
+
+ % Handle input ......................
+if nargin==0, help centroid, return, end
+if nargin==1
+  sz = size(x);
+  if sz(1)==2      % Matrix 2 by n
+    y = x(2,:); x = x(1,:);
+  elseif sz(2)==2  % Matrix n by 2
+    y = x(:,2); x = x(:,1);
+  else
+    y = imag(x);
+    x = real(x);
+  end
+end 
+
+ % Make a polygon closed ..............
+x = [x(:); x(1)];
+y = [y(:); y(1)];
+
+ % Check length .......................
+l = length(x);
+if length(y)~=l
+  error(' Vectors x and y must have the same length')
+end
+
+ % X-mean: Int{x^2*dy} ................
+del = y(2:l)-y(1:l-1);
+v = x(1:l-1).^2+x(2:l).^2+x(1:l-1).*x(2:l);
+x0 = v'*del;
+
+ % Y-mean: Int{y^2*dx} ................
+del = x(2:l)-x(1:l-1);
+v = y(1:l-1).^2+y(2:l).^2+y(1:l-1).*y(2:l);
+y0 = v'*del;
+
+ % Calculate area: Int{y*dx} ..........
+a = (y(1:l-1)+y(2:l))'*del;
+tol= 2*eps;
+if abs(a)<tol
+  disp(' Warning: area of polygon is close to 0')
+  a = a+sign(a)*tol+(~a)*tol;
+end
+ % Multiplier
+a = 1/3/a;
+
+ % Divide by area .....................
+x0 = -x0*a;
+y0 =  y0*a;
+
+if nargout < 2, x0 = x0+i*y0; end
diff --git a/sourcecodes/bnt-master/KPMtools/polygon_intersect.m b/sourcecodes/bnt-master/KPMtools/polygon_intersect.m
new file mode 100644
index 00000000..9289f612
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/polygon_intersect.m
@@ -0,0 +1,60 @@
+function [is,S] = isintpl(x1,y1,x2,y2)
+% ISINTPL Check for intersection of polygons.
+%	[IS,S] = ISINTPL(X1,Y1,X2,Y2) Accepts coordinates
+%	X1,Y1 and X2, Y2 of two polygons. Returns scalar
+%	IS equal to 1 if these polygons intersect each other
+%	and 0 if they do not.
+%	Also returns Boolean matrix S of the size length(X1)
+%	by length(X2) so that {ij} element of which is 1 if 
+%	line segments i to i+1 of the first polygon and 
+%	j to j+1 of the second polygon intersect each other,
+%	0 if they don't and .5 if they "touch" each other.
+
+%  Copyright (c) 1995 by Kirill K. Pankratov,
+%       kirill@plume.mit.edu.
+%       06/20/95, 08/25/95
+
+
+ % Handle input ...................................
+if nargin==0, help isintpl, return, end
+if nargin<4
+  error(' Not enough input arguments ')
+end
+
+ % Make column vectors and check sizes ............
+x1 = x1(:); y1 = y1(:);
+x2 = x2(:); y2 = y2(:);
+l1 = length(x1);
+l2 = length(x2);
+if length(y1)~=l1 | length(y2)~=l2
+  error('(X1,Y1) and (X2,Y2) must pair-wise have the same length.')
+end
+
+ % Quick exit if empty
+if l1<1 | l2<1, is = []; S = []; return, end
+
+ % Check if their ranges are intersecting .........
+lim1 = [min(x1) max(x1)]';
+lim2 = [min(x2) max(x2)]';
+isx = interval(lim1,lim2);  % X-ranges
+lim1 = [min(y1) max(y1)]';
+lim2 = [min(y2) max(y2)]';
+isy = interval(lim1,lim2);  % Y-ranges
+is = isx & isy;
+S = zeros(l2,l1);
+
+if ~is, return, end  % Early exit if disparate limits
+
+ % Indexing .......................................
+[i11,i12] = meshgrid(1:l1,1:l2);
+[i21,i22] = meshgrid([2:l1 1],[2:l2 1]);
+i11 = i11(:); i12 = i12(:);
+i21 = i21(:); i22 = i22(:);
+
+ % Calculate matrix of intersections ..............
+S(:) = iscross([x1(i11) x1(i21)]',[y1(i11) y1(i21)]',...
+               [x2(i12) x2(i22)]',[y2(i12) y2(i22)]')';
+
+S = S';
+is  = any(any(S));
+
diff --git a/sourcecodes/bnt-master/KPMtools/previewfig.m b/sourcecodes/bnt-master/KPMtools/previewfig.m
new file mode 100644
index 00000000..6983699b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/previewfig.m
@@ -0,0 +1,49 @@
+function f = previewfig(h,varargin)
+%PREVIEWFIG  Preview a figure to be exported using EXPORTFIG.
+%   F = PREVIEWFIG(H) creates a preview of H with the default
+%   EXPORTFIG options and returns the preview's figure handle in F.
+%   F = PREVIEWFIG(H,OPTIONS) creates a preview with OPTIONS as
+%   described in EXPORTFIG.
+%   PREVIEWFIG(...,PARAM1,VAL1,PARAM2,VAL2,...) creates a preview
+%   with the specified parameter-value pairs to H as described in
+%   EXPORTFIG. 
+%
+%   See also EXPORTFIG, APPLYTOFIG, RESTOREFIG.
+
+%  Copyright 2000 Ben Hinkle
+%  Email bug reports and comments to bhinkle@mathworks.com
+
+filename = [tempname, '.png'];
+args = {'resolution',0,'format','png'};
+if nargin > 1
+  exportfig(h, filename, varargin{:}, args{:});
+else
+  exportfig(h, filename, args{:});
+end
+
+X = imread(filename,'png');
+height = size(X,1);
+width = size(X,2);
+delete(filename);
+f = figure( 'Name', 'Preview', ...
+	    'Menubar', 'none', ...
+	    'NumberTitle', 'off', ...
+	    'Visible', 'off');
+image(X);
+axis image;
+ax = findobj(f, 'type', 'axes');
+axesPos = [0 0 width height];
+set(ax, 'Units', 'pixels', ...
+	'Position', axesPos, ...
+	'Visible', 'off');
+figPos = get(f,'Position');
+rootSize = get(0,'ScreenSize');
+figPos(3:4) = axesPos(3:4);
+if figPos(1) + figPos(3) > rootSize(3)
+  figPos(1) = rootSize(3) - figPos(3) - 50;
+end
+if figPos(2) + figPos(4) > rootSize(4)
+  figPos(2) = rootSize(4) - figPos(4) - 50;
+end
+set(f, 'Position',figPos, ...
+       'Visible', 'on');
diff --git a/sourcecodes/bnt-master/KPMtools/process_options.m b/sourcecodes/bnt-master/KPMtools/process_options.m
new file mode 100644
index 00000000..5e17eb89
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/process_options.m
@@ -0,0 +1,132 @@
+% PROCESS_OPTIONS - Processes options passed to a Matlab function.
+%                   This function provides a simple means of
+%                   parsing attribute-value options.  Each option is
+%                   named by a unique string and is given a default
+%                   value.
+%
+% Usage:  [var1, var2, ..., varn[, unused]] = ...
+%           process_options(args, ...
+%                           str1, def1, str2, def2, ..., strn, defn)
+%
+% Arguments:   
+%            args            - a cell array of input arguments, such
+%                              as that provided by VARARGIN.  Its contents
+%                              should alternate between strings and
+%                              values.
+%            str1, ..., strn - Strings that are associated with a 
+%                              particular variable
+%            def1, ..., defn - Default values returned if no option
+%                              is supplied
+%
+% Returns:
+%            var1, ..., varn - values to be assigned to variables
+%            unused          - an optional cell array of those 
+%                              string-value pairs that were unused;
+%                              if this is not supplied, then a
+%                              warning will be issued for each
+%                              option in args that lacked a match.
+%
+% Examples:
+%
+% Suppose we wish to define a Matlab function 'func' that has
+% required parameters x and y, and optional arguments 'u' and 'v'.
+% With the definition
+%
+%   function y = func(x, y, varargin)
+%
+%     [u, v] = process_options(varargin, 'u', 0, 'v', 1);
+%
+% calling func(0, 1, 'v', 2) will assign 0 to x, 1 to y, 0 to u, and 2
+% to v.  The parameter names are insensitive to case; calling 
+% func(0, 1, 'V', 2) has the same effect.  The function call
+% 
+%   func(0, 1, 'u', 5, 'z', 2);
+%
+% will result in u having the value 5 and v having value 1, but
+% will issue a warning that the 'z' option has not been used.  On
+% the other hand, if func is defined as
+%
+%   function y = func(x, y, varargin)
+%
+%     [u, v, unused_args] = process_options(varargin, 'u', 0, 'v', 1);
+%
+% then the call func(0, 1, 'u', 5, 'z', 2) will yield no warning,
+% and unused_args will have the value {'z', 2}.  This behaviour is
+% useful for functions with options that invoke other functions
+% with options; all options can be passed to the outer function and
+% its unprocessed arguments can be passed to the inner function.
+
+% Copyright (C) 2002 Mark A. Paskin
+%
+% This program is free software; you can redistribute it and/or modify
+% it under the terms of the GNU General Public License as published by
+% the Free Software Foundation; either version 2 of the License, or
+% (at your option) any later version.
+%
+% This program is distributed in the hope that it will be useful, but
+% WITHOUT ANY WARRANTY; without even the implied warranty of
+% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+% General Public License for more details.
+%
+% You should have received a copy of the GNU General Public License
+% along with this program; if not, write to the Free Software
+% Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
+% USA.
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+function [varargout] = process_options(args, varargin)
+
+% Check the number of input arguments
+n = length(varargin);
+if (mod(n, 2))
+  error('Each option must be a string/value pair.');
+end
+
+% Check the number of supplied output arguments
+if (nargout < (n / 2))
+  error('Insufficient number of output arguments given');
+elseif (nargout == (n / 2))
+  warn = 1;
+  nout = n / 2;
+else
+  warn = 0;
+  nout = n / 2 + 1;
+end
+
+% Set outputs to be defaults
+varargout = cell(1, nout);
+for i=2:2:n
+  varargout{i/2} = varargin{i};
+end
+
+% Now process all arguments
+nunused = 0;
+for i=1:2:length(args)
+  found = 0;
+  for j=1:2:n
+    if strcmpi(args{i}, varargin{j})
+      varargout{(j + 1)/2} = args{i + 1};
+      found = 1;
+      break;
+    end
+  end
+  if (~found)
+    if (warn)
+      warning(sprintf('Option ''%s'' not used.', args{i}));
+      args{i}
+    else
+      nunused = nunused + 1;
+      unused{2 * nunused - 1} = args{i};
+      unused{2 * nunused} = args{i + 1};
+    end
+  end
+end
+
+% Assign the unused arguments
+if (~warn)
+  if (nunused)
+    varargout{nout} = unused;
+  else
+    varargout{nout} = cell(0);
+  end
+end
diff --git a/sourcecodes/bnt-master/KPMtools/rand_psd.m b/sourcecodes/bnt-master/KPMtools/rand_psd.m
new file mode 100644
index 00000000..c6fc6d32
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rand_psd.m
@@ -0,0 +1,13 @@
+function M = rand_psd(d, d2, k)
+% Create a random positive definite matrix of size d by d by k (k defaults to 1)
+% M = rand_psd(d, d2, k)   default: d2 = d, k = 1
+
+if nargin<2, d2 = d; end
+if nargin<3, k = 1; end
+if d2 ~= d, error('must be square'); end
+
+M = zeros(d,d,k);
+for i=1:k
+  A = rand(d);
+  M(:,:,i) = A*A';
+end
diff --git a/sourcecodes/bnt-master/KPMtools/rectintC.m b/sourcecodes/bnt-master/KPMtools/rectintC.m
new file mode 100644
index 00000000..0651519b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rectintC.m
@@ -0,0 +1,22 @@
+function [overlap, normoverlap] = rectintC(A,B)
+%
+% A(i,:) = [x y w h]
+% B(j,:) = [x y w h]
+% overlap(i,j) = area of intersection
+% normoverlap(i,j) = overlap(i,j) / min(area(i), area(j))
+%
+% Same as built-in rectint, but faster and uses less memory (since avoids repmat).
+
+
+leftA = A(:,1);
+bottomA = A(:,2);
+rightA = leftA + A(:,3);
+topA = bottomA + A(:,4);
+
+leftB = B(:,1)';
+bottomB = B(:,2)';
+rightB = leftB + B(:,3)';
+topB = bottomB + B(:,4)';
+
+verbose = 0;
+[overlap, normoverlap] = rectintLoopC(leftA, rightA, topA, bottomA, leftB, rightB, topB, bottomB, verbose);
diff --git a/sourcecodes/bnt-master/KPMtools/rectintLoopC.c b/sourcecodes/bnt-master/KPMtools/rectintLoopC.c
new file mode 100644
index 00000000..1a106e04
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rectintLoopC.c
@@ -0,0 +1,71 @@
+
+#include "mex.h"
+#include <stdio.h>
+
+#define MAX(x,y)  ((x)>(y) ? (x) : (y))
+#define MIN(x,y)  ((x)<(y) ? (x) : (y))
+
+void mexFunction(
+        int nlhs,       mxArray *plhs[],
+        int nrhs, const mxArray *prhs[]
+        )
+{
+  int j,k,m,n,nzmax,*irs,*jcs, *irs2, *jcs2;
+  double *overlap, *overlap2, tmp, areaA, areaB;
+  double *leftA, *rightA, *topA, *bottomA;
+  double *leftB, *rightB, *topB, *bottomB;
+  double *verbose;
+
+  m = MAX(mxGetM(prhs[0]), mxGetN(prhs[0]));
+  n = MAX(mxGetM(prhs[4]), mxGetN(prhs[4]));
+  /* printf("A=%d, B=%d\n", m, n); */
+
+  leftA = mxGetPr(prhs[0]);
+  rightA = mxGetPr(prhs[1]);
+  topA = mxGetPr(prhs[2]);
+  bottomA = mxGetPr(prhs[3]);
+
+  leftB = mxGetPr(prhs[4]);
+  rightB = mxGetPr(prhs[5]);
+  topB = mxGetPr(prhs[6]);
+  bottomB = mxGetPr(prhs[7]);
+
+  verbose = mxGetPr(prhs[8]);
+
+  plhs[0] = mxCreateDoubleMatrix(m,n, mxREAL);
+  overlap  = mxGetPr(plhs[0]);
+
+  plhs[1] = mxCreateDoubleMatrix(m,n, mxREAL);
+  overlap2  = mxGetPr(plhs[1]);
+
+  k = 0; 
+  for (j = 0; (j < n); j++) {
+    int i;
+    for (i = 0; (i < m); i++) {
+      tmp = (MAX(0, MIN(rightA[i], rightB[j]) - MAX(leftA[i], leftB[j]) )) * 
+	(MAX(0, MIN(topA[i], topB[j]) - MAX(bottomA[i], bottomB[j]) ));
+
+      if (tmp > 0) {
+	overlap[k] = tmp;
+	
+	areaA = (rightA[i]-leftA[i])*(topA[i]-bottomA[i]);
+	areaB = (rightB[j]-leftB[j])*(topB[j]-bottomB[j]);
+	overlap2[k] = tmp/MIN(areaA, areaB);
+	
+	if (*verbose) {
+	  printf("j=%d,i=%d,overlap=%5.3f, norm=%5.3f\n", j,i, overlap[k], overlap2[k]);
+	}
+      }
+
+      k++;
+    }
+  }
+}
+
+
+
+
+
+
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/rectintLoopC.dll b/sourcecodes/bnt-master/KPMtools/rectintLoopC.dll
new file mode 100644
index 00000000..ab7750f6
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rectintLoopC.dll
Binary files differdiff --git a/sourcecodes/bnt-master/KPMtools/rectintSparse.m b/sourcecodes/bnt-master/KPMtools/rectintSparse.m
new file mode 100644
index 00000000..f2aa33a9
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rectintSparse.m
@@ -0,0 +1,59 @@
+function [overlap, normoverlap] = rectintSparse(A,B)
+%
+% A(i,:) = [x y w h]
+% B(j,:) = [x y w h]
+% overlap(i,j) = area of intersection
+% normoverla(i,j)
+%
+% Same as built-in rectint, but uses less memory.
+% Use rectintSparseC for a faster version.
+%
+
+leftA = A(:,1);
+bottomA = A(:,2);
+rightA = leftA + A(:,3);
+topA = bottomA + A(:,4);
+
+leftB = B(:,1)';
+bottomB = B(:,2)';
+rightB = leftB + B(:,3)';
+topB = bottomB + B(:,4)';
+
+numRectA = size(A,1);
+numRectB = size(B,1);
+
+%out = rectintSparseLoopC(leftA, rightA, topA, bottomA, leftB, rightB, topB, bottomB);
+
+nnz = ceil(0.2*numRectA*numRectB); % guess of number of non-zeroes
+overlap = sparse([], [], [], numRectA, numRectB, nnz);
+normoverlap = sparse([], [], [], numRectA, numRectB, nnz);
+for j=1:numRectB
+  for i=1:numRectA
+    tmp = (max(0, min(rightA(i), rightB(j)) - max(leftA(i), leftB(j)) ) ) .* ...
+	(max(0, min(topA(i), topB(j)) - max(bottomA(i), bottomB(j)) ) );
+    if tmp>0
+      overlap(i,j) = tmp;
+      areaA = (rightA(i)-leftA(i))*(topA(i)-bottomA(i));
+      areaB = (rightB(j)-leftB(j))*(topB(j)-bottomB(j));
+      normoverlap(i,j) = min(tmp/areaA, tmp/areaB);
+    end
+    %fprintf('j=%d, i=%d, overlap=%5.3f, norm=%5.3f\n',...
+    %	    j, i, overlap(i,j), normoverlap(i,j));
+  end
+end
+
+
+if 0
+N = size(bboxDense01,2); % 1000;
+rect = bboxToRect(bboxDense01)';
+A = rect(1:2,:);
+B = rect(1:N,:);
+
+tic; out1 = rectint(A, B); toc
+tic; out2 = rectintSparse(A, B); toc
+tic; out3 = rectintSparseC(A, B); toc
+tic; out4 = rectintC(A, B); toc
+assert(approxeq(out1, out2))
+assert(approxeq(out1, full(out3)))
+assert(approxeq(out1, out4))
+end
diff --git a/sourcecodes/bnt-master/KPMtools/rectintSparseC.m b/sourcecodes/bnt-master/KPMtools/rectintSparseC.m
new file mode 100644
index 00000000..401d7dc3
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rectintSparseC.m
@@ -0,0 +1,32 @@
+function [overlap, normoverlap] = rectintSparseC(A,B)
+%
+% function [area, normarea] = rectintSparseC(A,B)
+% A(i,:) = [x y w h]
+% B(j,:) = [x y w h]
+% out(i,j) = area of intersection
+%
+% Same as built-in rectint, but uses less memory.
+% Also, returns area of overlap normalized by area of patch.
+% See rectintSparse
+
+if isempty(A) | isempty(B)
+  overlap = [];
+  normoverlap = [];
+  return;
+end
+
+leftA = A(:,1);
+bottomA = A(:,2);
+rightA = leftA + A(:,3);
+topA = bottomA + A(:,4);
+
+leftB = B(:,1)';
+bottomB = B(:,2)';
+rightB = leftB + B(:,3)';
+topB = bottomB + B(:,4)';
+
+numRectA = size(A,1);
+numRectB = size(B,1);
+
+verbose = 0;
+[overlap, normoverlap] = rectintSparseLoopC(leftA, rightA, topA, bottomA, leftB, rightB, topB, bottomB, verbose);
diff --git a/sourcecodes/bnt-master/KPMtools/rectintSparseLoopC.c b/sourcecodes/bnt-master/KPMtools/rectintSparseLoopC.c
new file mode 100644
index 00000000..38ed08d5
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rectintSparseLoopC.c
@@ -0,0 +1,147 @@
+/* This is based on
+http://www.mathworks.com/access/helpdesk/help/techdoc/matlab_external/ch04cr12.shtml
+
+See rectintSparse.m for the matlab version of this code.
+
+*/
+
+#include <math.h> /* Needed for the ceil() prototype. */
+#include "mex.h"
+#include <stdio.h>
+
+/* If you are using a compiler that equates NaN to be zero, you 
+ * must compile this example using the flag  -DNAN_EQUALS_ZERO.
+ * For example:
+ *
+ *     mex -DNAN_EQUALS_ZERO fulltosparse.c
+ *
+ * This will correctly define the IsNonZero macro for your C
+ * compiler.
+ */
+
+#if defined(NAN_EQUALS_ZERO)
+#define IsNonZero(d) ((d) != 0.0 || mxIsNaN(d))
+#else
+#define IsNonZero(d) ((d) != 0.0)
+#endif
+
+#define MAX(x,y)  ((x)>(y) ? (x) : (y))
+#define MIN(x,y)  ((x)<(y) ? (x) : (y))
+
+void mexFunction(
+        int nlhs,       mxArray *plhs[],
+        int nrhs, const mxArray *prhs[]
+        )
+{
+  /* Declare variables. */
+  int j,k,m,n,nzmax,*irs,*jcs, *irs2, *jcs2;
+  double *overlap, *overlap2, tmp, areaA, areaB;
+  double percent_sparse;
+  double *leftA, *rightA, *topA, *bottomA;
+  double *leftB, *rightB, *topB, *bottomB;
+  double *verbose;
+
+  /* Get the size and pointers to input data. */
+  m = MAX(mxGetM(prhs[0]), mxGetN(prhs[0]));
+  n = MAX(mxGetM(prhs[4]), mxGetN(prhs[4]));
+  /* printf("A=%d, B=%d\n", m, n); */
+
+  leftA = mxGetPr(prhs[0]);
+  rightA = mxGetPr(prhs[1]);
+  topA = mxGetPr(prhs[2]);
+  bottomA = mxGetPr(prhs[3]);
+
+  leftB = mxGetPr(prhs[4]);
+  rightB = mxGetPr(prhs[5]);
+  topB = mxGetPr(prhs[6]);
+  bottomB = mxGetPr(prhs[7]);
+
+  verbose = mxGetPr(prhs[8]);
+
+    /* Allocate space for sparse matrix. 
+     * NOTE:  Assume at most 20% of the data is sparse.  Use ceil
+     * to cause it to round up. 
+     */
+
+  percent_sparse = 0.01;
+  nzmax = (int)ceil((double)m*(double)n*percent_sparse);
+
+  plhs[0] = mxCreateSparse(m,n,nzmax,0);
+  overlap  = mxGetPr(plhs[0]);
+  irs = mxGetIr(plhs[0]);
+  jcs = mxGetJc(plhs[0]);
+
+  plhs[1] = mxCreateSparse(m,n,nzmax,0);
+  overlap2  = mxGetPr(plhs[1]);
+  irs2 = mxGetIr(plhs[1]);
+  jcs2 = mxGetJc(plhs[1]);
+
+    
+  /* Assign nonzeros. */
+  k = 0; 
+  for (j = 0; (j < n); j++) {
+    int i;
+    jcs[j] = k; 
+    jcs2[j] = k; 
+    for (i = 0; (i < m); i++) {
+      tmp = (MAX(0, MIN(rightA[i], rightB[j]) - MAX(leftA[i], leftB[j]) )) * 
+	(MAX(0, MIN(topA[i], topB[j]) - MAX(bottomA[i], bottomB[j]) ));
+      
+      if (*verbose) {
+	printf("j=%d,i=%d,tmp=%5.3f\n", j,i,tmp);
+      }
+
+      if (IsNonZero(tmp)) {
+
+        /* Check to see if non-zero element will fit in 
+         * allocated output array.  If not, increase
+         * percent_sparse by 20%, recalculate nzmax, and augment
+         * the sparse array.
+         */
+        if (k >= nzmax) {
+          int oldnzmax = nzmax;
+          percent_sparse += 0.2;
+          nzmax = (int)ceil((double)m*(double)n*percent_sparse);
+
+          /* Make sure nzmax increases atleast by 1. */
+          if (oldnzmax == nzmax) 
+            nzmax++;
+	  printf("reallocating from %d to %d\n", oldnzmax, nzmax);
+
+          mxSetNzmax(plhs[0], nzmax); 
+          mxSetPr(plhs[0], mxRealloc(overlap, nzmax*sizeof(double)));
+          mxSetIr(plhs[0], mxRealloc(irs, nzmax*sizeof(int)));
+          overlap  = mxGetPr(plhs[0]);
+          irs = mxGetIr(plhs[0]);
+
+          mxSetNzmax(plhs[1], nzmax); 
+          mxSetPr(plhs[1], mxRealloc(overlap2, nzmax*sizeof(double)));
+          mxSetIr(plhs[1], mxRealloc(irs2, nzmax*sizeof(int)));
+          overlap2  = mxGetPr(plhs[1]);
+          irs2 = mxGetIr(plhs[1]);
+        }
+
+        overlap[k] = tmp;
+        irs[k] = i;
+	
+	areaA = (rightA[i]-leftA[i])*(topA[i]-bottomA[i]);
+	areaB = (rightB[j]-leftB[j])*(topB[j]-bottomB[j]);
+	overlap2[k] = MIN(tmp/areaA, tmp/areaB);
+	irs2[k] = i;
+
+        k++;
+      } /* IsNonZero */
+    } /* for i */
+  }
+  jcs[n] = k;
+  jcs2[n] = k;
+  
+}
+
+
+
+
+
+
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/rectintSparseLoopC.dll b/sourcecodes/bnt-master/KPMtools/rectintSparseLoopC.dll
new file mode 100644
index 00000000..ea535baa
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rectintSparseLoopC.dll
Binary files differdiff --git a/sourcecodes/bnt-master/KPMtools/repmatC.c b/sourcecodes/bnt-master/KPMtools/repmatC.c
new file mode 100644
index 00000000..6062772c
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/repmatC.c
@@ -0,0 +1,149 @@
+/*
+mex -c mexutil.c
+mex repmat.c mexutil.obj
+to check for warnings:
+gcc -Wall -I/cygdrive/c/MATLAB6p1/extern/include -c repmat.c
+*/
+#include "mexutil.h"
+#include <string.h>
+
+/* repeat a block of memory rep times */
+void memrep(char *dest, size_t chunk, int rep)
+{
+#if 0
+  /* slow way */
+  int i;
+  char *p = dest;
+  for(i=1;i<rep;i++) {
+    p += chunk;
+    memcpy(p, dest, chunk);
+  }
+#else
+  /* fast way */
+  if(rep == 1) return;
+  memcpy(dest + chunk, dest, chunk); 
+  if(rep & 1) {
+    dest += chunk;
+    memcpy(dest + chunk, dest, chunk);
+  }
+  /* now repeat using a block twice as big */
+  memrep(dest, chunk<<1, rep>>1);
+#endif
+}
+
+void repmat(char *dest, const char *src, int ndim, int *destdimsize, 
+	    int *dimsize, const int *dims, int *rep) 
+{
+  int d = ndim-1;
+  int i, chunk;
+  /* copy the first repetition into dest */
+  if(d == 0) {
+    chunk = dimsize[0];
+    memcpy(dest,src,chunk);
+  }
+  else {
+    /* recursively repeat each slice of src */
+    for(i=0;i<dims[d];i++) {
+      repmat(dest + i*destdimsize[d-1], src + i*dimsize[d-1], 
+	     ndim-1, destdimsize, dimsize, dims, rep);
+    }
+    chunk = destdimsize[d-1]*dims[d];
+  }
+  /* copy the result rep-1 times */
+  memrep(dest,chunk,rep[d]);
+}
+
+void mexFunction(int nlhs, mxArray *plhs[],
+                 int nrhs, const mxArray *prhs[])
+{
+  const mxArray *srcmat;
+  int ndim, *dimsize, eltsize;
+  const int *dims;
+  int ndimdest, *destdims, *destdimsize;
+  char *src, *dest;
+  int *rep;
+  int i,nrep;
+  int extra_rep = 1;
+  int empty;
+
+  if(nrhs < 2) mexErrMsgTxt("Usage: xrepmat(A, [N M ...])");
+  srcmat = prhs[0];
+  if(mxIsSparse(srcmat)) {
+    mexErrMsgTxt("Sorry, can't handle sparse matrices yet.");
+  }
+  if(mxIsCell(srcmat)) {
+    mexErrMsgTxt("Sorry, can't handle cell arrays yet.");
+  }
+  ndim = mxGetNumberOfDimensions(srcmat);
+  dims = mxGetDimensions(srcmat);
+  eltsize = mxGetElementSize(srcmat);
+
+  /* compute dimension sizes */
+  dimsize = mxCalloc(ndim, sizeof(int));
+  dimsize[0] = eltsize*dims[0];
+  for(i=1;i<ndim;i++) dimsize[i] = dimsize[i-1]*dims[i];
+
+  /* determine repetition vector */
+  ndimdest = ndim;
+  if(nrhs == 2) {
+    nrep = mxGetN(prhs[1]);
+    if(nrep > ndimdest) ndimdest = nrep;
+    rep = mxCalloc(ndimdest, sizeof(int));
+    for(i=0;i<nrep;i++) {
+      double repv = mxGetPr(prhs[1])[i];
+      rep[i] = (int)repv;
+    }
+    if(nrep == 1) {
+      /* special behavior */
+      nrep = 2;
+      rep[1] = rep[0];
+    }
+  }
+  else {
+    nrep = nrhs-1;
+    if(nrep > ndimdest) ndimdest = nrep;
+    rep = mxCalloc(ndimdest, sizeof(int));
+    for(i=0;i<nrep;i++) {
+      rep[i] = (int)*mxGetPr(prhs[i+1]);
+    }
+  }
+  for(i=nrep;i<ndimdest;i++) rep[i] = 1;
+
+  /* compute output size */
+  destdims = mxCalloc(ndimdest, sizeof(int));
+  for(i=0;i<ndim;i++) destdims[i] = dims[i]*rep[i];
+  for(;i<ndimdest;i++) { 
+    destdims[i] = rep[i];
+    extra_rep *= rep[i];
+  }
+  destdimsize = mxCalloc(ndim, sizeof(int));
+  destdimsize[0] = eltsize*destdims[0];
+  for(i=1;i<ndim;i++) destdimsize[i] = destdimsize[i-1]*destdims[i];
+
+    
+  /* for speed, array should be uninitialized */
+  plhs[0] = mxCreateNumericArray(ndimdest, destdims, mxGetClassID(srcmat), 
+				  mxIsComplex(srcmat)?mxCOMPLEX:mxREAL);
+
+  /* if any rep[i] == 0, output should be empty array.
+     Added by KPM 11/13/02.
+  */
+  empty = 0;
+  for (i=0; i < nrep; i++) {
+    if (rep[i]==0) 
+      empty = 1;
+  }
+  if (empty) 
+    return;
+
+  src = (char*)mxGetData(srcmat);
+  dest = (char*)mxGetData(plhs[0]);
+  repmat(dest,src,ndim,destdimsize,dimsize,dims,rep);
+  if(ndimdest > ndim) memrep(dest,destdimsize[ndim-1],extra_rep);
+  if(mxIsComplex(srcmat)) {
+    src = (char*)mxGetPi(srcmat);
+    dest = (char*)mxGetPi(plhs[0]);
+    repmat(dest,src,ndim,destdimsize,dimsize,dims,rep);
+    if(ndimdest > ndim) memrep(dest,destdimsize[ndim-1],extra_rep);
+  }
+}
diff --git a/sourcecodes/bnt-master/KPMtools/repmatC.dll b/sourcecodes/bnt-master/KPMtools/repmatC.dll
new file mode 100644
index 00000000..3b9ed6cb
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/repmatC.dll
Binary files differdiff --git a/sourcecodes/bnt-master/KPMtools/rgb2grayKPM.m b/sourcecodes/bnt-master/KPMtools/rgb2grayKPM.m
new file mode 100644
index 00000000..e15434f0
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rgb2grayKPM.m
@@ -0,0 +1,11 @@
+function g = rgb2grayKPM(rgb)
+% function g = rgb2grayKPM(rgb)
+% rgb2grayKPM Like the built-in function, but if r is already gray, does not cause an error
+
+[nr nc ncolors] = size(rgb);
+if ncolors > 1
+  g = rgb2gray(rgb);
+else
+  g = rgb;
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/rnd_partition.m b/sourcecodes/bnt-master/KPMtools/rnd_partition.m
new file mode 100644
index 00000000..da01bf08
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rnd_partition.m
@@ -0,0 +1,13 @@
+function [train, test] = rnd_partition(data, train_percent);
+% function [train, test] = rnd_partition(data, train_percent);
+%
+% data(:,i) is the i'th example
+% train_percent of these columns get put into train, the rest into test
+
+N = size(data, 2);
+ndx = randperm(N);
+k = ceil(N*train_percent);
+train_ndx = ndx(1:k);
+test_ndx = ndx(k+1:end);
+train =  data(:, train_ndx);
+test = data(:, test_ndx);
diff --git a/sourcecodes/bnt-master/KPMtools/rotate_xlabel.m b/sourcecodes/bnt-master/KPMtools/rotate_xlabel.m
new file mode 100644
index 00000000..35f7c48c
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/rotate_xlabel.m
@@ -0,0 +1,37 @@
+function hText = rotate_xlabel(degrees, newlabels)
+
+% Posted to comp.soft-sys.matlab on 2003-05-01 13:45:36 PST 
+% by David Borger (borger@ix.netcom.com)
+
+xtl = get(gca,'XTickLabel');
+set(gca,'XTickLabel','');
+lxtl = length(xtl);
+xtl = newlabels;
+if 0 % nargin>1
+    lnl = length(newlabels);
+    if lnl~=lxtl
+        error('Number of new labels must equal number of old');
+    end;
+    xtl = newlabels;
+end;
+
+
+hxLabel=get(gca,'XLabel');
+xLP=get(hxLabel,'Position');
+y=xLP(2);
+XTick=get(gca,'XTick');
+y=repmat(y,length(XTick),1);
+%fs=get(gca,'fontsize');
+fs = 12;
+hText=text(XTick,y,xtl,'fontsize',fs);
+set(hText,'Rotation',degrees,'HorizontalAlignment','right');
+
+% Modifications by KPM
+
+ylim = get(gca,'ylim');
+height = ylim(2)-ylim(1);
+N = length(hText);
+for i=1:N
+  voffset = ylim(2) - 0*height;
+  set(hText(i), 'position', [i voffset 0]);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/safeStr.m b/sourcecodes/bnt-master/KPMtools/safeStr.m
new file mode 100644
index 00000000..f775a2a9
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/safeStr.m
@@ -0,0 +1,5 @@
+function s = safeStr(s)
+% Change punctuation characters to they print properly
+
+s = strrep(s, '\', '/');
+s = strrep(s, '_', '-');
diff --git a/sourcecodes/bnt-master/KPMtools/sampleUniformInts.m b/sourcecodes/bnt-master/KPMtools/sampleUniformInts.m
new file mode 100644
index 00000000..d4c6c1a4
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/sampleUniformInts.m
@@ -0,0 +1,6 @@
+function M = sampleUniformInts(N, r, c)
+
+% M is an rxc matrix of integers in 1..N
+
+prob = normalize(ones(N,1));
+M = sample_discrete(prob, r, c);
diff --git a/sourcecodes/bnt-master/KPMtools/sample_discrete.m b/sourcecodes/bnt-master/KPMtools/sample_discrete.m
new file mode 100644
index 00000000..d8f6b687
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/sample_discrete.m
@@ -0,0 +1,40 @@
+function M = sample_discrete(prob, r, c)
+% SAMPLE_DISCRETE Like the built in 'rand', except we draw from a non-uniform discrete distrib.
+% M = sample_discrete(prob, r, c)
+%
+% Example: sample_discrete([0.8 0.2], 1, 10) generates a row vector of 10 random integers from {1,2},
+% where the prob. of being 1 is 0.8 and the prob of being 2 is 0.2.
+
+n = length(prob);
+
+if nargin == 1
+  r = 1; c = 1;
+elseif nargin == 2
+  c == r;
+end
+
+R = rand(r, c);
+M = ones(r, c);
+cumprob = cumsum(prob(:));
+
+if n < r*c
+  for i = 1:n-1
+    M = M + (R > cumprob(i));
+  end
+else
+  % loop over the smaller index - can be much faster if length(prob) >> r*c
+  cumprob2 = cumprob(1:end-1);
+  for i=1:r
+    for j=1:c
+      M(i,j) = sum(R(i,j) > cumprob2)+1;
+    end
+  end
+end
+
+
+% Slower, even though vectorized
+%cumprob = reshape(cumsum([0 prob(1:end-1)]), [1 1 n]);
+%M = sum(R(:,:,ones(n,1)) > cumprob(ones(r,1),ones(c,1),:), 3);
+
+% convert using a binning algorithm
+%M=bindex(R,cumprob);
diff --git a/sourcecodes/bnt-master/KPMtools/set_xtick_label.m b/sourcecodes/bnt-master/KPMtools/set_xtick_label.m
new file mode 100644
index 00000000..72f0f170
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/set_xtick_label.m
@@ -0,0 +1,51 @@
+function set_xtick_label(tick_labels, angle, axis_label)
+% SET_XTICK_LABEL Print the xtick labels at an angle instead of horizontally
+% set_xtick_label(tick_labels, angle, axis_label)
+%
+% angle default = 90
+% axis_label default = ''
+%
+% This is derived from Solution Number: 5375 on mathworks.com
+% See set_xtick_label_demo for an example
+
+if nargin < 2, angle = 90; end
+if nargin < 3, axis_label = []; end
+
+% Reduce the size of the axis so that all the labels fit in the figure.
+pos = get(gca,'Position');
+%set(gca,'Position',[pos(1), .2, pos(3) .65])
+%set(gca,'Position',[pos(1), 0, pos(3) .45])
+%set(gca,'Position',[pos(1), 0.1, pos(3) 0.5])
+
+ax = axis;    % Current axis limits
+axis(axis);    % Fix the axis limits
+Yl = ax(3:4);  % Y-axis limits
+
+%set(gca, 'xtick', 1:length(tick_labels));
+set(gca, 'xtick', 0.7:1:length(tick_labels));
+Xt = get(gca, 'xtick');
+
+% Place the text labels
+t = text(Xt,Yl(1)*ones(1,length(Xt)),tick_labels);
+set(t,'HorizontalAlignment','right','VerticalAlignment','top', 'Rotation', angle);
+
+% Remove the default labels
+set(gca,'XTickLabel','')
+
+% Get the Extent of each text object.  This
+% loop is unavoidable.
+for i = 1:length(t)
+  ext(i,:) = get(t(i),'Extent');
+end
+
+% Determine the lowest point.  The X-label will be
+% placed so that the top is aligned with this point.
+LowYPoint = min(ext(:,2));
+
+% Place the axis label at this point
+if ~isempty(axis_label)
+  Xl = get(gca, 'Xlim');
+  XMidPoint = Xl(1)+abs(diff(Xl))/2;
+  tl = text(XMidPoint,LowYPoint, axis_label, 'VerticalAlignment','top', ...
+	    'HorizontalAlignment','center');
+end
diff --git a/sourcecodes/bnt-master/KPMtools/set_xtick_label_demo.m b/sourcecodes/bnt-master/KPMtools/set_xtick_label_demo.m
new file mode 100644
index 00000000..e7c71f80
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/set_xtick_label_demo.m
@@ -0,0 +1,52 @@
+
+% Generate some test data.  Assume that the X-axis represents months.
+x = 1:12;
+y = 10*rand(1,length(x));
+
+% Plot the data.
+h = plot(x,y,'+');
+
+% Add a title.
+title('This is a title')
+
+% Set the X-Tick locations so that every other month is labeled.
+Xt = 1:2:11;
+Xl = [1 12];
+set(gca,'XTick',Xt,'XLim',Xl);
+
+% Add the months as tick labels.
+months = ['Jan';
+	  'Feb';
+	  'Mar';
+	  'Apr';
+	  'May';
+	  'Jun';
+	  'Jul';
+	  'Aug';
+	  'Sep';
+	  'Oct';
+	  'Nov';
+	  'Dec'];
+
+set_xtick_label(months(1:2:12, :), 90, 'xaxis label');
+
+
+
+if 0
+
+
+% Generate some test data.  Assume that the X-axis represents months.
+x = 1:8;
+y = 10*rand(1,length(x));
+
+% Plot the data.
+h = plot(x,y,'+');
+
+S = subsets(1:3);
+str = cell(1,8);
+for i=1:2^3
+  str{i} = num2str(S{i});
+end
+set_xtick_label(str);
+
+end
diff --git a/sourcecodes/bnt-master/KPMtools/setdiag.m b/sourcecodes/bnt-master/KPMtools/setdiag.m
new file mode 100644
index 00000000..30bfa60a
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/setdiag.m
@@ -0,0 +1,21 @@
+function M = setdiag(M, v)
+% SETDIAG Set the diagonal of a matrix to a specified scalar/vector.
+% M = set_diag(M, v)
+
+n = length(M);
+if length(v)==1
+  v = repmat(v, 1, n);
+end
+
+% e.g., for 3x3 matrix,  elements are numbered
+% 1 4 7 
+% 2 5 8 
+% 3 6 9
+% so diagnoal = [1 5 9]
+
+
+J = 1:n+1:n^2;
+M(J) = v;
+
+%M = triu(M,1) + tril(M,-1) + diag(v);
+
diff --git a/sourcecodes/bnt-master/KPMtools/softeye.m b/sourcecodes/bnt-master/KPMtools/softeye.m
new file mode 100644
index 00000000..29f45ee4
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/softeye.m
@@ -0,0 +1,11 @@
+function M = softeye(K, p)
+% SOFTEYE Make a stochastic matrix with p on the diagonal, and the remaining mass distributed uniformly
+% M = softeye(K, p)
+%
+% M is a K x K matrix.
+
+M = p*eye(K);
+q = 1-p;
+for i=1:K
+  M(i, [1:i-1  i+1:K]) = q/(K-1);
+end
diff --git a/sourcecodes/bnt-master/KPMtools/sort_evec.m b/sourcecodes/bnt-master/KPMtools/sort_evec.m
new file mode 100644
index 00000000..e934aa56
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/sort_evec.m
@@ -0,0 +1,22 @@
+function [evec, evals] = sort_evec(temp_evec, temp_evals, N)
+
+if ~isvectorBNT(temp_evals)
+  temp_evals = diag(temp_evals);
+end
+
+% Eigenvalues nearly always returned in descending order, but just
+% to make sure.....
+[evals perm] = sort(-temp_evals);
+evals = -evals(1:N);
+if evals == temp_evals(1:N)
+  % Originals were in order
+  evec = temp_evec(:, 1:N);
+  return
+else
+  fprintf('sorting evec\n');
+  % Need to reorder the eigenvectors
+  for i=1:N
+    evec(:,i) = temp_evec(:,perm(i));
+  end
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/splitLongSeqIntoManyShort.m b/sourcecodes/bnt-master/KPMtools/splitLongSeqIntoManyShort.m
new file mode 100644
index 00000000..e96d45f8
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/splitLongSeqIntoManyShort.m
@@ -0,0 +1,16 @@
+function short = splitLongSeqIntoManyShort(long, Tsmall)
+% splitLongSeqIntoManyShort Put groups of columns  into a cell array of narrower matrices
+% function short = splitLongSeqIntoManyShort(long, Tsmall)
+%
+% long(:,t)
+% short{i} = long(:,ndx1:ndx2) where each segment (except maybe the last) is of length Tsmall
+
+T = length(long);
+Nsmall = ceil(T/Tsmall);
+short = cell(Nsmall,1);
+
+t = 1;
+for i=1:Nsmall
+  short{i} = long(:,t:min(T,t+Tsmall-1));
+  t = t+Tsmall;
+end
diff --git a/sourcecodes/bnt-master/KPMtools/sprintf_intvec.m b/sourcecodes/bnt-master/KPMtools/sprintf_intvec.m
new file mode 100644
index 00000000..673ab922
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/sprintf_intvec.m
@@ -0,0 +1,9 @@
+function s = sprintf_intvec(v)
+% SPRINTF_INTVEC Print a vector of ints as comma separated string, with no trailing comma
+% function s = sprintf_intvec(v)
+%
+% e.g., sprintf_intvec(1:3) returns '1,2,3' 
+
+s = sprintf('%d,', v);
+s = s(1:end-1);
+
diff --git a/sourcecodes/bnt-master/KPMtools/sqdist.m b/sourcecodes/bnt-master/KPMtools/sqdist.m
new file mode 100644
index 00000000..45d1b18b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/sqdist.m
@@ -0,0 +1,29 @@
+function m = sqdist(p, q, A)
+% SQDIST      Squared Euclidean or Mahalanobis distance.
+% SQDIST(p,q)   returns m(i,j) = (p(:,i) - q(:,j))'*(p(:,i) - q(:,j)).
+% SQDIST(p,q,A) returns m(i,j) = (p(:,i) - q(:,j))'*A*(p(:,i) - q(:,j)).
+
+%  From Tom Minka's lightspeed toolbox
+
+[d, pn] = size(p);
+[d, qn] = size(q);
+
+if nargin == 2
+  
+  pmag = sum(p .* p, 1);
+  qmag = sum(q .* q, 1);
+  m = repmat(qmag, pn, 1) + repmat(pmag', 1, qn) - 2*p'*q;
+  %m = ones(pn,1)*qmag + pmag'*ones(1,qn) - 2*p'*q;
+  
+else
+
+  if isempty(A) | isempty(p)
+    error('sqdist: empty matrices');
+  end
+  Ap = A*p;
+  Aq = A*q;
+  pmag = sum(p .* Ap, 1);
+  qmag = sum(q .* Aq, 1);
+  m = repmat(qmag, pn, 1) + repmat(pmag', 1, qn) - 2*p'*Aq;
+  
+end
diff --git a/sourcecodes/bnt-master/KPMtools/strmatch_multi.m b/sourcecodes/bnt-master/KPMtools/strmatch_multi.m
new file mode 100644
index 00000000..c29f326d
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/strmatch_multi.m
@@ -0,0 +1,30 @@
+function [posns] = strmatch_multi(keys, strs)
+% STRMATCH_MULTI Find where each key occurs in list of strings.
+% [pos] = strmatch_multi(key, strs) where key is a string and strs is a cell array of strings
+% works like the built-in command sequence pos = strmatch(key, strs, 'exact'),
+% except that pos is the first occurrence of key in strs; if there is no occurence, pos is 0.
+%
+% [posns] = strmatch_multi(keys, strs), where keys is a cell array of strings, 
+% matches each element of keys. It loops over whichever is shorter, keys or strs.
+
+if ~iscell(keys), keys = {keys}; end
+nkeys = length(keys);
+posns = zeros(1, nkeys);
+if length(keys) < length(strs)
+  for i=1:nkeys
+    %pos = strmatch(keys{i}, strs, 'exact');
+    ndx = strcmp(keys{i}, strs); % faster
+    pos = find(ndx);
+    if ~isempty(pos)
+      posns(i) = pos(1);
+    end
+  end
+else
+  for s=1:length(strs)
+    %ndx = strmatch(strs{s}, keys, 'exact');
+    ndx = strcmp(strs{s}, keys);
+    ndx = find(ndx);
+    posns(ndx) = s;
+  end
+end
+
diff --git a/sourcecodes/bnt-master/KPMtools/strmatch_substr.m b/sourcecodes/bnt-master/KPMtools/strmatch_substr.m
new file mode 100644
index 00000000..7a1e431f
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/strmatch_substr.m
@@ -0,0 +1,28 @@
+function ndx = strmatch_substr(str, strs)
+% STRMATCH_SUBSTR Like strmatch, except str can match any part of strs{i}, not just prefix.
+% ndx = strmatch_substr(str, strs)
+%
+% Example:
+% i = strmatch('max', {'max','minimax','maximum'})
+%  returns i = [1; 3] since only 1 and 3 begin with max, but
+% i = strmatch_substr('max', {'max','minimax','maximum'})
+%  returns i = [1;2;3];
+%
+% If str is also a cell array, it is like calling strmatch_substr several times
+% and concatenating the results. 
+% Example:
+% 
+% i = strmatch_substr({'foo', 'dog'}, {'foo', 'hoofoo', 'dog'}) 
+%   returns i = [1;2;3]
+
+ndx = [];
+if ~iscell(str), str = {str}; end
+for j=1:length(str)
+  for i=1:length(strs)
+    %ind = strfind(strs{i}, str{j}); % not supported in 6.0
+    ind = findstr(strs{i}, str{j});
+    if ~isempty(ind)
+      ndx = [ndx; i];
+    end
+  end
+end
diff --git a/sourcecodes/bnt-master/KPMtools/strsplit.m b/sourcecodes/bnt-master/KPMtools/strsplit.m
new file mode 100644
index 00000000..695c1635
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/strsplit.m
@@ -0,0 +1,53 @@
+function parts = strsplit(splitstr, str, option)
+%STRSPLIT Split string into pieces.
+%
+%   STRSPLIT(SPLITSTR, STR, OPTION) splits the string STR at every occurrence
+%   of SPLITSTR and returns the result as a cell array of strings.  By default,
+%   SPLITSTR is not included in the output.
+%
+%   STRSPLIT(SPLITSTR, STR, OPTION) can be used to control how SPLITSTR is
+%   included in the output.  If OPTION is 'include', SPLITSTR will be included
+%   as a separate string.  If OPTION is 'append', SPLITSTR will be appended to
+%   each output string, as if the input string was split at the position right
+%   after the occurrence SPLITSTR.  If OPTION is 'omit', SPLITSTR will not be
+%   included in the output.
+
+%   Author:      Peter J. Acklam
+%   Time-stamp:  2004-09-22 08:48:01 +0200
+%   E-mail:      pjacklam@online.no
+%   URL:         http://home.online.no/~pjacklam
+
+   nargsin = nargin;
+   error(nargchk(2, 3, nargsin));
+   if nargsin < 3
+      option = 'omit';
+   else
+      option = lower(option);
+   end
+
+   splitlen = length(splitstr);
+   parts = {};
+
+   while 1
+
+      k = strfind(str, splitstr);
+      if isempty(k)
+         parts{end+1} = str;
+         break
+      end
+
+      switch option
+         case 'include'
+            parts(end+1:end+2) = {str(1:k(1)-1), splitstr};
+         case 'append'
+            parts{end+1} = str(1 : k(1)+splitlen-1);
+         case 'omit'
+            parts{end+1} = str(1 : k(1)-1);
+         otherwise
+            error(['Invalid option string -- ', option]);
+      end
+
+
+      str = str(k(1)+splitlen : end);
+
+   end
diff --git a/sourcecodes/bnt-master/KPMtools/subplot2.m b/sourcecodes/bnt-master/KPMtools/subplot2.m
new file mode 100644
index 00000000..fb8c1c2f
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/subplot2.m
@@ -0,0 +1,17 @@
+function subplot2(nrows, ncols, i, j)
+% function subplot2(nrows, ncols, i, j)
+
+
+sz = [nrows ncols];
+%k = sub2ind(sz, i, j)
+k = sub2ind(sz(end:-1:1), j, i);
+subplot(nrows, ncols, k);
+
+if 0
+  ncols_plot = ceil(sqrt(Nplots));
+  nrows_plot = ceil(Nplots/ncols_plot);
+  Nplots = nrows_plot*ncols_plot;
+  for p=1:Nplots
+    subplot(nrows_plot, ncols_plot, p);
+  end
+end
diff --git a/sourcecodes/bnt-master/KPMtools/subplot3.m b/sourcecodes/bnt-master/KPMtools/subplot3.m
new file mode 100644
index 00000000..0f8d1cc3
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/subplot3.m
@@ -0,0 +1,13 @@
+function fignum = subplot3(nrows, ncols, fignumBase, plotnumBase)
+% function subplot3(nrows, ncols, fignumBase, plotnumBase)
+% Choose a subplot number, opening a new figure if necessary
+% eg nrows=2, ncols = 2, we plot on (fignum, plotnum) = (1,1), (1,2), (1,3), (1,4), (2,1), ...
+
+nplotsPerFig = nrows*ncols;
+fignum = fignumBase + div(plotnumBase-1, nplotsPerFig);
+plotnum = wrap(plotnumBase, nplotsPerFig);
+figure(fignum);
+if plotnum==1, clf; end
+subplot(nrows, ncols, plotnum);
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/subsets.m b/sourcecodes/bnt-master/KPMtools/subsets.m
new file mode 100644
index 00000000..47f999f0
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/subsets.m
@@ -0,0 +1,58 @@
+function [T, bitv] = subsets(S, U, L, sorted, N)
+% SUBSETS Create a set of all the subsets of S which have cardinality <= U and >= L
+% T = subsets(S, U, L)
+% U defaults to length(S), L defaults to 0.
+% So subsets(S) generates the powerset of S.
+%
+% Example:
+% T = subsets(1:4, 2, 1) 
+% T{:} = 1, 2, [1 2], 3, [1 3], [2 3], 4, [1 4], [2 4], [3 4]
+%
+% T = subsets(S, U, L, sorted)
+% If sorted=1, return the subsets in increasing size
+%
+% Example:
+% T = subsets(1:4, 2, 1, 1) 
+% T{:} = 1, 2, 3, 4, [1 2], [1 3], [2 3], [1 4], [2 4], [3 4]
+%
+% [T, bitv] = subsets(S, U, L, sorted, N)
+% Row i of bitv is a bit vector representation of T{i},
+% where bitv has N columns (representing 1:N).
+% N defaults to max(S).
+%
+% Example:
+% [T,bitv] = subsets(2:4, 2^3, 0, 0, 5)
+% T{:} = [], 2, 3, [2 3], 4, [2 4], [3 4], [2 3 4]
+% bitv=
+%     0     0     0     0     0
+%     0     1     0     0     0
+%     0     0     1     0     0
+%     0     1     1     0     0
+%     0     0     0     1     0
+%     0     1     0     1     0
+%     0     0     1     1     0
+%     0     1     1     1     0
+
+n = length(S);
+
+if nargin < 2, U = n; end
+if nargin < 3, L = 0; end
+if nargin < 4, sorted = 0; end
+if nargin < 5, N = max(S); end
+
+bits = ind2subv(2*ones(1,n), 1:2^n)-1;
+sm = sum(bits,2);
+masks = bits((sm <= U) & (sm >= L), :);
+m = size(masks, 1);
+T = cell(1, m);
+for i=1:m
+  s = S(find(masks(i,:)));
+  T{i} = s;
+end
+
+if sorted 
+  T = sortcell(T);
+end
+
+bitv = zeros(m, N);
+bitv(:, S) = masks;
diff --git a/sourcecodes/bnt-master/KPMtools/subsets1.m b/sourcecodes/bnt-master/KPMtools/subsets1.m
new file mode 100644
index 00000000..ca2bf46c
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/subsets1.m
@@ -0,0 +1,45 @@
+function sub_s=subsets1(s,k)
+% SUBSETS1 creates sub-sets of a specific from a given set
+% SS = subsets1(S, k)
+% 
+% S is the given set
+% k is the required sub-sets size
+% 
+% Example:
+% 
+% >> ss=subsets1([1:4],3);
+% >> ss{:}
+% ans =
+%      1     2     3
+% ans =
+%      1     2     4
+% ans =
+%      1     3     4
+% ans =
+%      2     3     4
+% 
+% Written by Raanan Yehezkel, 2004
+
+if k<0 % special case
+    error('subset size must be positive');
+elseif k==0 % special case
+    sub_s={[]};
+else
+    l=length(s);
+    ss={};
+    if l>=k
+        if k==1 % Exit condition
+            for I=1:l
+                ss{I}=s(I);
+            end
+        else
+            for I=1:l
+                ss1=subsets1(s([(I+1):l]),k-1);
+                for J=1:length(ss1)
+                    ss{end+1}=[s(I),ss1{J}];
+                end
+            end
+        end
+    end
+    sub_s=ss;
+end
diff --git a/sourcecodes/bnt-master/KPMtools/subsetsFixedSize.m b/sourcecodes/bnt-master/KPMtools/subsetsFixedSize.m
new file mode 100644
index 00000000..26808e86
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/subsetsFixedSize.m
@@ -0,0 +1,45 @@
+function sub_s=subsets1(s,k)
+% SUBSETS1 creates sub-sets of a specific size from a given set
+% SS = subsets1(S, k)
+% 
+% S is the given set
+% k is the required sub-sets size
+% 
+% Example:
+% 
+% >> ss=subsets1([1:4],3);
+% >> ss{:}
+% ans =
+%      1     2     3
+% ans =
+%      1     2     4
+% ans =
+%      1     3     4
+% ans =
+%      2     3     4
+% 
+% Written by Raanan Yehezkel, 2004
+
+if k<0 % special case
+    error('subset size must be positive');
+elseif k==0 % special case
+    sub_s={[]};
+else
+    l=length(s);
+    ss={};
+    if l>=k
+        if k==1 % Exit condition
+            for I=1:l
+                ss{I}=s(I);
+            end
+        else
+            for I=1:l
+                ss1=subsets1(s([(I+1):l]),k-1);
+                for J=1:length(ss1)
+                    ss{end+1}=[s(I),ss1{J}];
+                end
+            end
+        end
+    end
+    sub_s=ss;
+end
diff --git a/sourcecodes/bnt-master/KPMtools/subv2ind.m b/sourcecodes/bnt-master/KPMtools/subv2ind.m
new file mode 100644
index 00000000..dd50360d
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/subv2ind.m
@@ -0,0 +1,17 @@
+function index = subv2ind(siz,sub)
+%SUBV2IND   Linear index from subscript vector.
+% SUBV2IND(SIZ,SUB) returns an equivalent single index corresponding to a
+% subscript vector for an array of size SIZ.
+% If SUB is a matrix, with subscript vectors as rows, then the result is a 
+% column vector.
+%
+% This is the opposite of IND2SUBV, so that
+%   SUBV2IND(SIZ,IND2SUBV(SIZ,IND)) == IND.
+%
+% See also IND2SUBV, SUB2IND.
+
+%index = subv2indTest(siz,sub);
+prev_cum_size = [1 cumprod(siz(1:end-1))];
+%index = (sub-1)*prev_cum_size' + 1;
+index = sub*prev_cum_size' - sum(prev_cum_size) + 1;
+
diff --git a/sourcecodes/bnt-master/KPMtools/subv2indKPM.c b/sourcecodes/bnt-master/KPMtools/subv2indKPM.c
new file mode 100644
index 00000000..e1ecff42
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/subv2indKPM.c
@@ -0,0 +1,89 @@
+/* C mex version of subv2ind*/
+/* 2 inputs, 1 output       */
+/* siz, subv                */
+/* ndx                      */
+#include "mex.h"
+
+void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[]){
+	int    i, j, k, nCol, nRow, binary, temp;
+	double *pSize, *pSubv, *pr;
+	int    *cumprod;
+
+	pSize = mxGetPr(prhs[0]);
+	pSubv = mxGetPr(prhs[1]);
+	nCol  = mxGetNumberOfElements(prhs[0]);
+	nRow  = mxGetM(prhs[1]);
+
+	
+	if(mxIsEmpty(prhs[1])){
+		plhs[0] = mxCreateDoubleMatrix(0, 0, mxREAL);
+		return;
+	}
+
+	if(mxIsEmpty(prhs[0])){
+		plhs[0] = mxCreateDoubleMatrix(1, 1, mxREAL);
+		*mxGetPr(plhs[0]) = 1;
+		return;
+	}
+
+	binary = 2;
+	for (i = 0; i < nCol; i++){
+		if (pSize[i] > 2.0){
+			binary = 0;
+			break;
+		}
+		else if(pSize[i] == 1.0){
+			binary = 1;
+		}
+	}
+
+	plhs[0] = mxCreateDoubleMatrix(nRow, 1, mxREAL);
+	pr = mxGetPr(plhs[0]);
+	for(i=0; i<nRow; i++){
+		pr[i] = 1.0;
+	}
+
+	if (binary == 2){
+		for(j=0; j<nCol; j++){
+			temp = j * nRow;
+			for(i=0; i<nRow; i++){
+				pr[i] += ((int)pSubv[temp + i] - 1) << j;
+			}
+		}
+	}
+	else if(binary == 1){	
+		cumprod = malloc(nCol * sizeof(int));
+		cumprod[0] = 1;
+		for(i=1; i<nCol; i++){
+			k = (int)pSize[i-1] - 1;
+			cumprod[i] = cumprod[i-1] << k;
+		}
+		for(j=0; j<nCol; j++){
+			temp = j * nRow;
+			for(i=0; i<nRow; i++){
+				k = (int)pSubv[temp + i] - 1;
+				if(k)pr[i] += cumprod[j];
+			}
+		}
+		free(cumprod);
+	}
+	else {
+		cumprod = malloc(nCol * sizeof(int));
+		cumprod[0] = 1;
+		for(i=1; i<nCol; i++){
+			k = (int)pSize[i-1];
+			cumprod[i] = cumprod[i-1] * k;
+		}
+		for(j=0; j<nCol; j++){
+			temp = j * nRow;
+			for(i=0; i<nRow; i++){
+				k = (int)pSubv[temp + i] - 1;
+				pr[i] += cumprod[j] * k;
+			}
+		}
+		free(cumprod);
+	}
+}
+
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/subv2indKPM.m b/sourcecodes/bnt-master/KPMtools/subv2indKPM.m
new file mode 100644
index 00000000..d0a16618
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/subv2indKPM.m
@@ -0,0 +1,66 @@
+function ndx = subv2indKPM(siz, subv)
+% SUBV2IND Like the built-in sub2ind, but the subscripts are given as row vectors.
+% ind = subv2ind(siz,subv)
+%
+% siz can be a row or column vector of size d.
+% subv should be a collection of N row vectors of size d.
+% ind will be of size N * 1.
+%
+% Example:
+% subv = [1 1 1;
+%         2 1 1;
+%         ...
+%         2 2 2];
+% subv2ind([2 2 2], subv) returns [1 2 ... 8]'
+% i.e., the leftmost digit toggles fastest.
+%
+% See also IND2SUBV.
+
+
+if isempty(subv)
+  ndx = [];
+  return;
+end
+
+if isempty(siz)
+  ndx = 1;
+  return;
+end
+
+[ncases ndims] = size(subv);
+
+%if length(siz) ~= ndims
+%  error('length of subscript vector and sizes must be equal');
+%end
+
+if all(siz==2)
+  %rbits = subv(:,end:-1:1)-1; % read from right to left, convert to 0s/1s
+  %ndx = bitv2dec(rbits)+1; 
+  twos = pow2(0:ndims-1);
+  ndx = ((subv-1) * twos(:)) + 1;
+  %ndx = sum((subv-1) .* twos(ones(ncases,1), :), 2) + 1; % equivalent to matrix * vector
+  %ndx = sum((subv-1) .* repmat(twos, ncases, 1), 2) + 1; % much slower than ones
+  %ndx = ndx(:)';
+else
+  %siz = siz(:)';
+  cp = [1 cumprod(siz(1:end-1))]';
+  %ndx = ones(ncases, 1);
+  %for i = 1:ndims
+  %  ndx = ndx + (subv(:,i)-1)*cp(i);
+  %end
+  ndx = (subv-1)*cp + 1;
+end
+
+%%%%%%%%%%%
+
+function d = bitv2dec(bits)
+% BITV2DEC Convert a bit vector to a decimal integer
+% d = butv2dec(bits)
+%
+% This is just like the built-in bin2dec, except the argument is a vector, not a string.
+% If bits is an array, each row will be converted.
+
+[m n] = size(bits);
+twos = pow2(n-1:-1:0);
+d = sum(bits .* twos(ones(m,1),:),2);
+
diff --git a/sourcecodes/bnt-master/KPMtools/subv2indMinka.m b/sourcecodes/bnt-master/KPMtools/subv2indMinka.m
new file mode 100644
index 00000000..cdb457b0
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/subv2indMinka.m
@@ -0,0 +1,17 @@
+function index = subv2indMinka(siz,sub)
+%SUBV2IND   Linear index from subscript vector.
+% SUBV2IND(SIZ,SUB) returns an equivalent single index corresponding to a
+% subscript vector for an array of size SIZ.
+% If SUB is a matrix, with subscript vectors as rows, then the result is a 
+% column vector.
+%
+% This is the opposite of IND2SUBV, so that
+%   SUBV2IND(SIZ,IND2SUBV(SIZ,IND)) == IND.
+%
+% See also IND2SUBV, SUB2IND.
+
+% Written by Tom Minka
+
+prev_cum_size = [1 cumprod(siz(1:end-1))];
+%index = (sub-1)*prev_cum_size' + 1;
+index = sub*prev_cum_size' - sum(prev_cum_size) + 1;
diff --git a/sourcecodes/bnt-master/KPMtools/subv2indTest.m b/sourcecodes/bnt-master/KPMtools/subv2indTest.m
new file mode 100644
index 00000000..e64ab947
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/subv2indTest.m
@@ -0,0 +1,15 @@
+function ndx = subv2indTest(siz,sub)
+%SUBV2IND   Linear index from subscript vector.
+% SUBV2IND(SIZ,SUB) returns an equivalent single index corresponding to a
+% subscript vector for an array of size SIZ.
+% If SUB is a matrix, with subscript vectors as rows, then the result is a 
+% column vector.
+%
+% This is the opposite of IND2SUBV, so that
+%   SUBV2IND(SIZ,IND2SUBV(SIZ,IND)) == IND.
+%
+% See also IND2SUBV, SUB2IND.
+
+ndx = subv2indMinka(siz,sub);
+ndx2 = subv2indKPM(siz,sub);
+assert(isequalKPM(ndx,ndx2))
diff --git a/sourcecodes/bnt-master/KPMtools/sumv.m b/sourcecodes/bnt-master/KPMtools/sumv.m
new file mode 100644
index 00000000..4086cae9
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/sumv.m
@@ -0,0 +1,11 @@
+function T2 = sumv(T1, sum_over)
+%
+% Like the built in sum, but will sum over several dimensions and then squeeze the result.
+
+T2 = T1;
+for i=1:length(sum_over)
+  if sum_over(i) <= ndims(T2) % prevent summing over non-existent dimensions
+    T2=sum(T2, sum_over(i));
+  end
+end
+T2 = squeeze(T2);
diff --git a/sourcecodes/bnt-master/KPMtools/suptitle.m b/sourcecodes/bnt-master/KPMtools/suptitle.m
new file mode 100644
index 00000000..fa12c541
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/suptitle.m
@@ -0,0 +1,105 @@
+function hout=suptitle(str, fs)
+%SUPTITLE Puts a title above all subplots.
+%	SUPTITLE('text') adds text to the top of the figure
+%	above all subplots (a "super title"). Use this function
+%	after all subplot commands.
+
+% Drea Thomas 6/15/95 drea@mathworks.com
+
+% Warning: If the figure or axis units are non-default, this
+% will break.
+
+% Parameters used to position the supertitle.
+
+% Amount of the figure window devoted to subplots
+plotregion = .92;
+
+% Y position of title in normalized coordinates
+titleypos  = .95;
+
+% Fontsize for supertitle
+if nargin < 2
+  fs = get(gcf,'defaultaxesfontsize')+4;
+end
+
+% Fudge factor to adjust y spacing between subplots
+fudge=1;
+
+haold = gca;
+figunits = get(gcf,'units');
+
+% Get the (approximate) difference between full height (plot + title
+% + xlabel) and bounding rectangle.
+
+	if (~strcmp(figunits,'pixels')),
+		set(gcf,'units','pixels');
+		pos = get(gcf,'position');
+		set(gcf,'units',figunits);
+	else,
+		pos = get(gcf,'position');
+	end
+	ff = (fs-4)*1.27*5/pos(4)*fudge;
+
+        % The 5 here reflects about 3 characters of height below
+        % an axis and 2 above. 1.27 is pixels per point.
+
+% Determine the bounding rectange for all the plots
+
+% h = findobj('Type','axes');   
+
+% findobj is a 4.2 thing.. if you don't have 4.2 comment out
+% the next line and uncomment the following block.
+	
+h = findobj(gcf,'Type','axes');  % Change suggested by Stacy J. Hills
+
+% If you don't have 4.2, use this code instead
+%ch = get(gcf,'children');
+%h=[];
+%for i=1:length(ch),
+%  if strcmp(get(ch(i),'type'),'axes'),
+%    h=[h,ch(i)];
+%  end
+%end
+
+	
+
+
+max_y=0;
+min_y=1;
+
+oldtitle =0;
+for i=1:length(h),
+	if (~strcmp(get(h(i),'Tag'),'suptitle')),
+		pos=get(h(i),'pos');
+		if (pos(2) < min_y), min_y=pos(2)-ff/5*3;end;
+		if (pos(4)+pos(2) > max_y), max_y=pos(4)+pos(2)+ff/5*2;end;
+	else,
+		oldtitle = h(i);
+	end
+end
+
+if max_y > plotregion,
+	scale = (plotregion-min_y)/(max_y-min_y);
+	for i=1:length(h),
+		pos = get(h(i),'position');
+		pos(2) = (pos(2)-min_y)*scale+min_y;
+		pos(4) = pos(4)*scale-(1-scale)*ff/5*3;
+		set(h(i),'position',pos);
+	end
+end
+
+np = get(gcf,'nextplot');
+set(gcf,'nextplot','add');
+if (oldtitle),
+	delete(oldtitle);
+end
+ha=axes('pos',[0 1 1 1],'visible','off','Tag','suptitle');
+ht=text(.5,titleypos-1,str);set(ht,'horizontalalignment','center','fontsize',fs);
+set(gcf,'nextplot',np);
+axes(haold);
+if nargout,
+	hout=ht;
+end
+
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/unaryEncoding.m b/sourcecodes/bnt-master/KPMtools/unaryEncoding.m
new file mode 100644
index 00000000..ab0316a3
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/unaryEncoding.m
@@ -0,0 +1,16 @@
+function U = unaryEncoding(data, K)
+% unaryEncoding Encode data(s) as a 1-of-K column vector
+% function U = unaryEncoding(data, K)
+%
+% eg.
+% If data = [3 2 2] and K=3,
+% then U = [0 0 0
+%           0 1 1
+%           1 0 0]
+
+if nargin < 2, K = max(data); end
+N = length(data);
+U = zeros(K,N);
+ndx = subv2ind([K N], [data(:)'; 1:N]');
+U(ndx) = 1;
+U = reshape(U, [K N]);
diff --git a/sourcecodes/bnt-master/KPMtools/wrap.m b/sourcecodes/bnt-master/KPMtools/wrap.m
new file mode 100644
index 00000000..9a5f2a2a
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/wrap.m
@@ -0,0 +1,7 @@
+function v = wrap(u,N)
+% WRAP Wrap a vector of indices around a torus.
+% v = wrap(u,N)
+%
+% e.g., wrap([-1 0 1 2 3 4], 3)   =   2 3 1 2 3 1
+
+v = mod(u-1,N)+1;       
diff --git a/sourcecodes/bnt-master/KPMtools/xticklabel_rotate90.m b/sourcecodes/bnt-master/KPMtools/xticklabel_rotate90.m
new file mode 100644
index 00000000..374c13b2
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/xticklabel_rotate90.m
@@ -0,0 +1,68 @@
+function xticklabel_rotate90(XTick,varargin)
+%XTICKLABEL_ROTATE90 - Rotate numeric Xtick labels by 90 degrees
+%
+% Syntax: xticklabel_rotate90(XTick)
+%
+% Input:  XTick - vector array of XTick positions & values (numeric)
+%
+% Output:  none
+%
+% Example 1:  Set the positions of the XTicks and rotate them
+%    figure;  plot([1960:2004],randn(45,1)); xlim([1960 2004]);
+%    xticklabel_rotate90([1960:2:2004]);
+%    %If you wish, you may set a few text "Property-value" pairs
+%    xticklabel_rotate90([1960:2:2004],'Color','m','Fontweight','bold');
+%
+% Example 2:  %Rotate XTickLabels at their current position
+%    XTick = get(gca,'XTick');
+%    xticklabel_rotate90(XTick);
+%
+% Other m-files required: none
+% Subfunctions: none
+% MAT-files required: none
+%
+% See also: TEXT,  SET
+
+% Author: Denis Gilbert, Ph.D., physical oceanography
+% Maurice Lamontagne Institute, Dept. of Fisheries and Oceans Canada
+% email: gilbertd@dfo-mpo.gc.ca  Web: http://www.qc.dfo-mpo.gc.ca/iml/
+% February 1998; Last revision: 24-Mar-2003
+
+if ~isnumeric(XTick)
+   error('XTICKLABEL_ROTATE90 requires a numeric input argument');
+end
+
+%Make sure XTick is a column vector
+XTick = XTick(:);
+
+%Set the Xtick locations and set XTicklabel to an empty string
+set(gca,'XTick',XTick,'XTickLabel','')
+
+% Define the xtickLabels
+xTickLabels = num2str(XTick);
+
+% Determine the location of the labels based on the position
+% of the xlabel
+hxLabel = get(gca,'XLabel');  % Handle to xlabel
+xLabelString = get(hxLabel,'String');
+
+if ~isempty(xLabelString)
+   warning('You may need to manually reset the XLABEL vertical position')
+end
+
+set(hxLabel,'Units','data');
+xLabelPosition = get(hxLabel,'Position');
+y = xLabelPosition(2);
+
+%CODE below was modified following suggestions from Urs Schwarz
+y=repmat(y,size(XTick,1),1);
+% retrieve current axis' fontsize
+fs = get(gca,'fontsize');
+
+% Place the new xTickLabels by creating TEXT objects
+hText = text(XTick, y, xTickLabels,'fontsize',fs);
+
+% Rotate the text objects by 90 degrees
+set(hText,'Rotation',90,'HorizontalAlignment','right',varargin{:})
+
+%------------- END OF CODE --------------
diff --git a/sourcecodes/bnt-master/KPMtools/zipload.m b/sourcecodes/bnt-master/KPMtools/zipload.m
new file mode 100644
index 00000000..a66dbd1b
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/zipload.m
@@ -0,0 +1,47 @@
+%ZIPLOAD   Load compressed data file created with ZIPSAVE
+%
+%	[data] = zipload( filename )
+%	filename: string variable that contains the name of the 
+%	compressed file (do not include '.zip' extension)
+%	Use only with files created with 'zipsave'
+%	pkzip25.exe has to be in the matlab path. This file is a compression utility 
+%	made by Pkware, Inc. It can be dowloaded from:	http://www.pkware.com
+%	Or directly from ftp://ftp.pkware.com/pk250c32.exe, for the Windows 95/NT version.
+%	This function was tested using 'PKZIP 2.50 Command Line for Windows 9x/NT'
+%	It is important to use version 2.5 of the utility. Otherwise the command line below
+%	has to be changed to include the proper options of the compression utility you 
+%	wish to use.
+%	This function was tested in MATLAB Version 5.3 under Windows NT.
+%	Fernando A. Brucher - May/25/1999
+%	
+%	Example:
+%		[loadedData] = zipload('testfile');
+%--------------------------------------------------------------------
+
+function [data] = zipload( filename )
+
+%--- Decompress data file by calling pkzip (comand line command) ---
+% 	Options used: 
+%	'extract' = decompress file
+%	'silent' = no console output 
+%	'over=all' = overwrite files
+
+%eval( ['!pkzip25 -extract -silent -over=all ', filename, '.zip'] )
+eval( ['!pkzip25 -extract -silent -over=all ', filename, '.zip'] )
+
+
+%--- Load data from decompressed file ---
+%	try, catch takes care of cases when pkzip fails to decompress a 
+%	valid matlab format file
+
+try
+   tmpStruc = load( filename );
+   data = tmpStruc.data;
+catch, return, end
+
+
+%--- Delete decompressed file ---
+
+delete( [filename,'.mat'] )
+
+
diff --git a/sourcecodes/bnt-master/KPMtools/zipsave.m b/sourcecodes/bnt-master/KPMtools/zipsave.m
new file mode 100644
index 00000000..81f8b20e
--- /dev/null
+++ b/sourcecodes/bnt-master/KPMtools/zipsave.m
@@ -0,0 +1,42 @@
+%ZIPSAVE   Save data in compressed format
+%
+%	zipsave( filename, data )
+%	filename: string variable that contains the name of the resulting 
+%	compressed file (do not include '.zip' extension)
+%	pkzip25.exe has to be in the matlab path. This file is a compression utility 
+%	made by Pkware, Inc. It can be dowloaded from: http://www.pkware.com
+%	This function was tested using 'PKZIP 2.50 Command Line for Windows 9x/NT'
+%	It is important to use version 2.5 of the utility. Otherwise the command line below
+%	has to be changed to include the proper options of the compression utility you 
+%	wish to use.
+%	This function was tested in MATLAB Version 5.3 under Windows NT.
+%	Fernando A. Brucher - May/25/1999
+%	
+%	Example:
+%		testData = [1 2 3; 4 5 6; 7 8 9];
+%		zipsave('testfile', testData);
+%
+% Modified by Kevin Murphy, 26 Feb 2004, to use winzip
+%------------------------------------------------------------------------
+
+function zipsave( filename, data )
+
+%--- Save data in a temporary file in matlab format (.mat)---
+
+eval( ['save ''', filename, ''' data'] )
+
+
+%--- Compress data by calling pkzip (comand line command) ---
+% 	Options used: 
+%	'add' = add compressed files to the resulting zip file
+%	'silent' = no console output 
+%	'over=all' = overwrite files
+
+%eval( ['!pkzip25 -silent -add -over=all ', filename, '.zip ', filename,'.mat'] )
+eval( ['!zip ', filename, '.zip ', filename,'.mat'] )
+
+%--- Delete temporary matlab format file ---
+
+delete( [filename,'.mat'] )
+
+