kinit.js 2.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110
  1. "use strict";
  2. var Distance = require("./distance.js"),
  3. eudist = Distance.eudist,
  4. dist = Distance.dist;
  5. module.exports = {
  6. kmrand: function kmrand(data, k) {
  7. var map = {},
  8. ks = [],
  9. t = k << 2;
  10. var len = data.length;
  11. var multi = data[0].length > 0;
  12. while (ks.length < k && t-- > 0) {
  13. var d = data[Math.floor(Math.random() * len)];
  14. var key = multi ? d.join("_") : "" + d;
  15. if (!map[key]) {
  16. map[key] = true;
  17. ks.push(d);
  18. }
  19. }
  20. if (ks.length < k) throw new Error("Error initializating clusters");else return ks;
  21. },
  22. /**
  23. * K-means++ initial centroid selection
  24. */
  25. kmpp: function kmpp(data, k) {
  26. var distance = data[0].length ? eudist : dist;
  27. var ks = [],
  28. len = data.length;
  29. var multi = data[0].length > 0;
  30. var map = {};
  31. // First random centroid
  32. var c = data[Math.floor(Math.random() * len)];
  33. var key = multi ? c.join("_") : "" + c;
  34. ks.push(c);
  35. map[key] = true;
  36. // Retrieve next centroids
  37. while (ks.length < k) {
  38. // Min Distances between current centroids and data points
  39. var dists = [],
  40. lk = ks.length;
  41. var dsum = 0,
  42. prs = [];
  43. for (var i = 0; i < len; i++) {
  44. var min = Infinity;
  45. for (var j = 0; j < lk; j++) {
  46. var _dist = distance(data[i], ks[j]);
  47. if (_dist <= min) min = _dist;
  48. }
  49. dists[i] = min;
  50. }
  51. // Sum all min distances
  52. for (var _i = 0; _i < len; _i++) {
  53. dsum += dists[_i];
  54. }
  55. // Probabilities and cummulative prob (cumsum)
  56. for (var _i2 = 0; _i2 < len; _i2++) {
  57. prs[_i2] = { i: _i2, v: data[_i2], pr: dists[_i2] / dsum, cs: 0 };
  58. }
  59. // Sort Probabilities
  60. prs.sort(function (a, b) {
  61. return a.pr - b.pr;
  62. });
  63. // Cummulative Probabilities
  64. prs[0].cs = prs[0].pr;
  65. for (var _i3 = 1; _i3 < len; _i3++) {
  66. prs[_i3].cs = prs[_i3 - 1].cs + prs[_i3].pr;
  67. }
  68. // Randomize
  69. var rnd = Math.random();
  70. // Gets only the items whose cumsum >= rnd
  71. var idx = 0;
  72. while (idx < len - 1 && prs[idx++].cs < rnd) {}
  73. ks.push(prs[idx - 1].v);
  74. /*
  75. let done = false;
  76. while(!done) {
  77. // this is our new centroid
  78. c = prs[idx-1].v
  79. key = multi? c.join("_") : `${c}`;
  80. if(!map[key]) {
  81. map[key] = true;
  82. ks.push(c);
  83. done = true;
  84. }
  85. else {
  86. idx++;
  87. }
  88. }
  89. */
  90. }
  91. return ks;
  92. }
  93. };
  94. //# sourceMappingURL=kinit.js.map