Algorithms_in_C  1.0.0
Set of algorithms implemented in C.
Kohonen SOM trace/chain algorithm
Collaboration diagram for Kohonen SOM trace/chain algorithm:

Macros

#define max(a, b)   (((a) > (b)) ? (a) : (b))
 shorthand for maximum value
 
#define min(a, b)   (((a) < (b)) ? (a) : (b))
 shorthand for minimum value
 

Functions

double _random (double a, double b)
 Helper function to generate a random number in a given interval. More...
 
int save_nd_data (const char *fname, double **X, int num_points, int num_features)
 Save a given n-dimensional data martix to file. More...
 
void kohonen_get_min_1d (double const *X, int N, double *val, int *idx)
 Get minimum value and index of the value in a vector. More...
 
void kohonen_update_weights (double const *x, double *const *W, double *D, int num_out, int num_features, double alpha, int R)
 Update weights of the SOM using Kohonen algorithm. More...
 
void kohonen_som_tracer (double **X, double *const *W, int num_samples, int num_features, int num_out, double alpha_min)
 Apply incremental algorithm with updating neighborhood and learning rates on all samples in the given datset. More...
 

Detailed Description

Function Documentation

◆ _random()

double _random ( double  a,
double  b 
)

Helper function to generate a random number in a given interval.


Steps:

  1. r1 = rand() % 100 gets a random number between 0 and 99
  2. r2 = r1 / 100 converts random number to be between 0 and 0.99
  3. scale and offset the random number to given range of \([a,b)\)

    \[ y = (b - a) \times \frac{\text{(random number between 0 and RAND_MAX)} \; \text{mod}\; 100}{100} + a \]

Parameters
alower limit
bupper limit
Returns
random number in the range \([a,b)\)
55 {
56  int r = rand() % 100;
57  return ((b - a) * r / 100.f) + a;
58 }

◆ kohonen_get_min_1d()

void kohonen_get_min_1d ( double const *  X,
int  N,
double *  val,
int *  idx 
)

Get minimum value and index of the value in a vector.

Parameters
[in]Xvector to search
[in]Nnumber of points in the vector
[out]valminimum value found
[out]idxindex where minimum value was found
105 {
106  val[0] = INFINITY; // initial min value
107 
108  for (int i = 0; i < N; i++) // check each value
109  {
110  if (X[i] < val[0]) // if a lower value is found
111  { // save the value and its index
112  idx[0] = i;
113  val[0] = X[i];
114  }
115  }
116 }

◆ kohonen_som_tracer()

void kohonen_som_tracer ( double **  X,
double *const *  W,
int  num_samples,
int  num_features,
int  num_out,
double  alpha_min 
)

Apply incremental algorithm with updating neighborhood and learning rates on all samples in the given datset.

Parameters
[in]Xdata set
[in,out]Wweights matrix
[in]num_samplesnumber of output points
[in]num_featuresnumber of features per input sample
[in]num_outnumber of output points
[in]alpha_minterminal value of alpha
181 {
182  int R = num_out >> 2, iter = 0;
183  double alpha = 1.f;
184  double *D = (double *)malloc(num_out * sizeof(double));
185 
186  // Loop alpha from 1 to alpha_min
187  for (; alpha > alpha_min; alpha -= 0.01, iter++)
188  {
189  // Loop for each sample pattern in the data set
190  for (int sample = 0; sample < num_samples; sample++)
191  {
192  const double *x = X[sample];
193  // update weights for the current input pattern sample
194  kohonen_update_weights(x, W, D, num_out, num_features, alpha, R);
195  }
196 
197  // every 10th iteration, reduce the neighborhood range
198  if (iter % 10 == 0 && R > 1)
199  R--;
200  }
201 
202  free(D);
203 }
Here is the call graph for this function:

◆ kohonen_update_weights()

void kohonen_update_weights ( double const *  x,
double *const *  W,
double *  D,
int  num_out,
int  num_features,
double  alpha,
int  R 
)

Update weights of the SOM using Kohonen algorithm.

Parameters
[in]xdata point
[in,out]Wweights matrix
[in,out]Dtemporary vector to store distances
[in]num_outnumber of output points
[in]num_featuresnumber of features per input sample
[in]alphalearning rate \(0<\alpha\le1\)
[in]Rneighborhood range
131 {
132  int j, k;
133 
134 #ifdef _OPENMP
135 #pragma omp for
136 #endif
137  // step 1: for each output point
138  for (j = 0; j < num_out; j++)
139  {
140  D[j] = 0.f;
141  // compute Euclidian distance of each output
142  // point from the current sample
143  for (k = 0; k < num_features; k++)
144  D[j] += (W[j][k] - x[k]) * (W[j][k] - x[k]);
145  }
146 
147  // step 2: get closest node i.e., node with smallest Euclidian distance to
148  // the current pattern
149  int d_min_idx;
150  double d_min;
151  kohonen_get_min_1d(D, num_out, &d_min, &d_min_idx);
152 
153  // step 3a: get the neighborhood range
154  int from_node = max(0, d_min_idx - R);
155  int to_node = min(num_out, d_min_idx + R + 1);
156 
157  // step 3b: update the weights of nodes in the
158  // neighborhood
159 #ifdef _OPENMP
160 #pragma omp for
161 #endif
162  for (j = from_node; j < to_node; j++)
163  for (k = 0; k < num_features; k++)
164  // update weights of nodes in the neighborhood
165  W[j][k] += alpha * (x[k] - W[j][k]);
166 }
Here is the call graph for this function:

◆ save_nd_data()

int save_nd_data ( const char *  fname,
double **  X,
int  num_points,
int  num_features 
)

Save a given n-dimensional data martix to file.

Parameters
[in]fnamefilename to save in (gets overwriten without confirmation)
[in]Xmatrix to save
[in]num_pointsrows in the matrix = number of points
[in]num_featurescolumns in the matrix = dimensions of points
Returns
0 if all ok
-1 if file creation failed
72 {
73  FILE *fp = fopen(fname, "wt");
74  if (!fp) // error with fopen
75  {
76  char msg[120];
77  sprintf(msg, "File error (%s): ", fname);
78  perror(msg);
79  return -1;
80  }
81 
82  for (int i = 0; i < num_points; i++) // for each point in the array
83  {
84  for (int j = 0; j < num_features; j++) // for each feature in the array
85  {
86  fprintf(fp, "%.4g", X[i][j]); // print the feature value
87  if (j < num_features - 1) // if not the last feature
88  fprintf(fp, ","); // suffix comma
89  }
90  if (i < num_points - 1) // if not the last row
91  fprintf(fp, "\n"); // start a new line
92  }
93  fclose(fp);
94  return 0;
95 }
kohonen_update_weights
void kohonen_update_weights(double const *x, double *const *W, double *D, int num_out, int num_features, double alpha, int R)
Update weights of the SOM using Kohonen algorithm.
Definition: kohonen_som_trace.c:129
min
#define min(a, b)
shorthand for minimum value
Definition: kohonen_som_trace.c:36
max
#define max(a, b)
shorthand for maximum value
Definition: kohonen_som_trace.c:32
kohonen_get_min_1d
void kohonen_get_min_1d(double const *X, int N, double *val, int *idx)
Get minimum value and index of the value in a vector.
Definition: kohonen_som_trace.c:104