mirror of
https://github.com/zenorogue/hyperrogue.git
synced 2025-06-20 15:24:07 +00:00
rogueviz:: added a header for kohonen.cpp and (newly added) embeddings.cpp
This commit is contained in:
parent
0fc8dfde15
commit
04c9bd193a
227
rogueviz/embeddings.cpp
Normal file
227
rogueviz/embeddings.cpp
Normal file
@ -0,0 +1,227 @@
|
|||||||
|
#include "kohonen.h"
|
||||||
|
|
||||||
|
namespace rogueviz {
|
||||||
|
|
||||||
|
namespace embeddings {
|
||||||
|
|
||||||
|
embedding_type etype = eNatural;
|
||||||
|
|
||||||
|
/** landscape embedding */
|
||||||
|
|
||||||
|
map<cell*, kohvec> landscape_at;
|
||||||
|
|
||||||
|
map<cellwalker, kohvec> delta_at;
|
||||||
|
|
||||||
|
void init_landscape(int dimensions) {
|
||||||
|
etype = eLandscape;
|
||||||
|
landscape_at.clear();
|
||||||
|
delta_at.clear();
|
||||||
|
landscape_at[currentmap->gamestart()].resize(dimensions, 0);
|
||||||
|
println(hlog, "initialized for ", currentmap->gamestart());
|
||||||
|
}
|
||||||
|
|
||||||
|
void normalize(cellwalker& cw) {
|
||||||
|
int d = celldist(cw.at);
|
||||||
|
back:
|
||||||
|
if(GDIM == 3) {
|
||||||
|
auto& da = currentmap->dirdist(cw.at);
|
||||||
|
for(int j=0; j<S7; j++) if(da[j] == 1) {
|
||||||
|
cellwalker str = currentmap->strafe(cw, j);
|
||||||
|
int d1 = celldist(str.at);
|
||||||
|
if(d1 == d+1) continue;
|
||||||
|
else if(d1 == d-1) { d = d1; cw = str; goto back; }
|
||||||
|
else println(hlog, tie(d, d1));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if(S3 == OINF) return;
|
||||||
|
else if(S3 == 4) for(int s: {1, -1}) {
|
||||||
|
cellwalker str = (cw + s) + wstep + s;
|
||||||
|
int d1 = celldist(str.at);
|
||||||
|
if(d1 < d) { d = d1; cw = str; goto back; }
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
while(true) {
|
||||||
|
cellwalker str = (cw + 1) + wstep + 2;
|
||||||
|
int d1 = celldist(str.at);
|
||||||
|
if(d1 > d) break;
|
||||||
|
d = d1; cw = str;
|
||||||
|
}
|
||||||
|
while(true) {
|
||||||
|
cellwalker str = (cw - 2) + wstep - 1;
|
||||||
|
int d1 = celldist(str.at);
|
||||||
|
if(d1 > d) break;
|
||||||
|
d = d1; cw = str;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ld gaussian_random() {
|
||||||
|
return (hrand(1000) + hrand(1000) - hrand(1000) - hrand(1000)) / 1000.;
|
||||||
|
}
|
||||||
|
|
||||||
|
void apply_delta(cellwalker cw, kohvec& v) {
|
||||||
|
normalize(cw);
|
||||||
|
|
||||||
|
auto& da = delta_at[cw];
|
||||||
|
if(da.empty()) {
|
||||||
|
da.resize(isize(v));
|
||||||
|
for(auto& x: da) x = gaussian_random();
|
||||||
|
}
|
||||||
|
|
||||||
|
for(int i=0; i<isize(v); i++) v[i] += da[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
kohvec& get_landscape_at(cell *h) {
|
||||||
|
if(landscape_at.count(h)) return landscape_at[h];
|
||||||
|
|
||||||
|
int hd = celldist(h);
|
||||||
|
// if(hd > 2) exit(1);
|
||||||
|
for(int i=0; i<h->type; i++) {
|
||||||
|
cell *h1 = h->cmove(i);
|
||||||
|
auto hd1 = celldist(h1);
|
||||||
|
if(hd1 < hd) {
|
||||||
|
cellwalker cw(h, i);
|
||||||
|
auto& res = landscape_at[h];
|
||||||
|
res = get_landscape_at(h1);
|
||||||
|
if(S3 == 3) {
|
||||||
|
apply_delta(cw, res);
|
||||||
|
apply_delta(cw+1, res);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
apply_delta(cw, res);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return landscape_at[h];
|
||||||
|
}
|
||||||
|
|
||||||
|
/** signposts embedding */
|
||||||
|
|
||||||
|
vector<cell*> signposts;
|
||||||
|
|
||||||
|
void mark_signposts(bool full, const vector<cell*>& ac) {
|
||||||
|
etype = eSignpost;
|
||||||
|
println(hlog, "marking signposts");
|
||||||
|
signposts.clear();
|
||||||
|
int maxd = 0;
|
||||||
|
if(!bounded)
|
||||||
|
for(cell *c: ac) maxd = max(celldist(c), maxd);
|
||||||
|
for(cell *c: ac)
|
||||||
|
if(full || c->type != 6)
|
||||||
|
if(bounded || celldist(c) == maxd)
|
||||||
|
signposts.push_back(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
/** rug embedding */
|
||||||
|
|
||||||
|
map<cell*, hyperpoint> rug_coordinates;
|
||||||
|
|
||||||
|
void generate_rug(int i, bool close) {
|
||||||
|
etype = eHypersian;
|
||||||
|
rug::init();
|
||||||
|
while(rug::precision_increases < i) rug::physics();
|
||||||
|
if(close) rug::close();
|
||||||
|
for(auto p: rug::rug_map)
|
||||||
|
rug_coordinates[p.first] = p.second->native;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** main function */
|
||||||
|
|
||||||
|
void get_coordinates(kohvec& v, cell *c, cell *c0) {
|
||||||
|
|
||||||
|
switch(etype) {
|
||||||
|
case eLandscape: {
|
||||||
|
v = get_landscape_at(c);
|
||||||
|
columns = isize(v);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
case eSignpost:
|
||||||
|
columns = isize(signposts);
|
||||||
|
alloc(v);
|
||||||
|
for(int i=0; i<isize(signposts); i++)
|
||||||
|
v[i] = celldistance(signposts[i], c);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case eHypersian: {
|
||||||
|
columns = 3;
|
||||||
|
alloc(v);
|
||||||
|
auto h = rug_coordinates.at(c);
|
||||||
|
for(int i=0; i<3; i++) v[i] = h[i];
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
case eNatural: {
|
||||||
|
hyperpoint h = calc_relative_matrix(c, c0, C0) * C0;
|
||||||
|
|
||||||
|
using namespace euc;
|
||||||
|
auto& T0 = eu_input.user_axes;
|
||||||
|
|
||||||
|
if(sphere) {
|
||||||
|
columns = MDIM;
|
||||||
|
alloc(v);
|
||||||
|
for(int i=0; i<MDIM; i++)
|
||||||
|
v[i] = h[i];
|
||||||
|
}
|
||||||
|
else if(euclid && bounded && WDIM == 2 && T0[0][1] == 0 && T0[1][0] == 0 && T0[0][0] == T0[1][1]) {
|
||||||
|
columns = 6;
|
||||||
|
alloc(v);
|
||||||
|
int s = T0[0][0];
|
||||||
|
for(int i=0; i<3; i++) {
|
||||||
|
hyperpoint h1 = spin(120*degree*i) * h;
|
||||||
|
ld x = h1[1];
|
||||||
|
ld alpha = 2 * M_PI * x / s / (sqrt(3) / 2);
|
||||||
|
println(hlog, kz(x), " -> ", kz(alpha));
|
||||||
|
v[2*i] = cos(alpha);
|
||||||
|
v[2*i+1] = sin(alpha);
|
||||||
|
}
|
||||||
|
println(hlog, kz(h), " -> ", v);
|
||||||
|
}
|
||||||
|
else if(euclid && bounded && WDIM == 2) {
|
||||||
|
columns = 4;
|
||||||
|
alloc(v);
|
||||||
|
rug::clifford_torus ct;
|
||||||
|
h = ct.torus_to_s4(ct.actual_to_torus(h));
|
||||||
|
for(int i=0; i<4; i++)
|
||||||
|
v[i] = h[i];
|
||||||
|
}
|
||||||
|
else if(euclid && bounded && WDIM == 3) {
|
||||||
|
columns = 6;
|
||||||
|
alloc(v);
|
||||||
|
using namespace euc;
|
||||||
|
auto& T0 = eu_input.user_axes;
|
||||||
|
for(int i=0; i<3; i++) {
|
||||||
|
int s = T0[i][i];
|
||||||
|
ld alpha = 2 * M_PI * h[i] / s;
|
||||||
|
v[2*i] = cos(alpha) * s;
|
||||||
|
v[2*i+1] = sin(alpha) * s;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if(euclid && !quotient) {
|
||||||
|
columns = WDIM;
|
||||||
|
alloc(v);
|
||||||
|
for(int i=0; i<WDIM; i++)
|
||||||
|
v[i] = h[i];
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
println(hlog, "error: unknown geometry to get coordinates from");
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
case eProjection: {
|
||||||
|
hyperpoint h = calc_relative_matrix(c, c0, C0) * C0;
|
||||||
|
hyperpoint res;
|
||||||
|
applymodel(shiftless(h), res);
|
||||||
|
columns = WDIM;
|
||||||
|
if(models::is_3d(pconf)) columns = 3;
|
||||||
|
alloc(v);
|
||||||
|
for(int i=0; i<columns; i++) v[i] = res[i];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
@ -4,27 +4,12 @@
|
|||||||
// Kohonen's self-organizing maps.
|
// Kohonen's self-organizing maps.
|
||||||
// This is a part of RogueViz, not a part of HyperRogue.
|
// This is a part of RogueViz, not a part of HyperRogue.
|
||||||
|
|
||||||
#include "rogueviz.h"
|
#include "kohonen.h"
|
||||||
|
|
||||||
namespace rogueviz { namespace kohonen {
|
namespace rogueviz { namespace kohonen {
|
||||||
|
|
||||||
void initialize_neurons();
|
|
||||||
void initialize_neurons_initial();
|
|
||||||
void initialize_dispersion();
|
|
||||||
void initialize_samples_to_show();
|
|
||||||
void clear();
|
|
||||||
void create_neurons();
|
|
||||||
|
|
||||||
|
|
||||||
int columns;
|
int columns;
|
||||||
|
|
||||||
typedef vector<double> kohvec;
|
|
||||||
|
|
||||||
struct sample {
|
|
||||||
kohvec val;
|
|
||||||
string name;
|
|
||||||
};
|
|
||||||
|
|
||||||
vector<sample> data;
|
vector<sample> data;
|
||||||
|
|
||||||
map<int, int> sample_vdata_id;
|
map<int, int> sample_vdata_id;
|
||||||
@ -33,17 +18,6 @@ int whattodraw[3] = {-2,-2,-2};
|
|||||||
|
|
||||||
int min_group = 10, max_group = 10;
|
int min_group = 10, max_group = 10;
|
||||||
|
|
||||||
struct neuron {
|
|
||||||
kohvec net;
|
|
||||||
cell *where;
|
|
||||||
double udist;
|
|
||||||
int lpbak;
|
|
||||||
color_t col;
|
|
||||||
int allsamples, drawn_samples, csample, bestsample, max_group_here;
|
|
||||||
int debug;
|
|
||||||
neuron() { drawn_samples = allsamples = bestsample = 0; max_group_here = max_group; debug = 0; }
|
|
||||||
};
|
|
||||||
|
|
||||||
vector<string> colnames;
|
vector<string> colnames;
|
||||||
|
|
||||||
kohvec weights;
|
kohvec weights;
|
||||||
@ -52,8 +26,6 @@ vector<neuron> net;
|
|||||||
|
|
||||||
int neuronId(neuron& n) { return &n - &(net[0]); }
|
int neuronId(neuron& n) { return &n - &(net[0]); }
|
||||||
|
|
||||||
void alloc(kohvec& k) { k.resize(columns); }
|
|
||||||
|
|
||||||
bool neurons_indexed = false;
|
bool neurons_indexed = false;
|
||||||
|
|
||||||
int samples;
|
int samples;
|
||||||
@ -710,12 +682,6 @@ void step() {
|
|||||||
|
|
||||||
int initdiv = 1;
|
int initdiv = 1;
|
||||||
|
|
||||||
flagtype KS_ROGUEVIZ = 1;
|
|
||||||
flagtype KS_NEURONS = 2;
|
|
||||||
flagtype KS_DISPERSION = 4;
|
|
||||||
flagtype KS_SAMPLES = 8;
|
|
||||||
flagtype KS_NEURONS_INI = 16;
|
|
||||||
|
|
||||||
flagtype state = 0;
|
flagtype state = 0;
|
||||||
|
|
||||||
vector<double> bdiffs;
|
vector<double> bdiffs;
|
||||||
|
95
rogueviz/kohonen.h
Normal file
95
rogueviz/kohonen.h
Normal file
@ -0,0 +1,95 @@
|
|||||||
|
/* a header file for kohonen and embedding */
|
||||||
|
#ifndef _KOHONEN_H_
|
||||||
|
#define _KOHONEN_H_
|
||||||
|
|
||||||
|
#include "rogueviz.h"
|
||||||
|
|
||||||
|
namespace rogueviz {
|
||||||
|
|
||||||
|
namespace kohonen {
|
||||||
|
|
||||||
|
typedef vector<double> kohvec;
|
||||||
|
|
||||||
|
static const flagtype KS_ROGUEVIZ = 1;
|
||||||
|
static const flagtype KS_NEURONS = 2;
|
||||||
|
static const flagtype KS_DISPERSION = 4;
|
||||||
|
static const flagtype KS_SAMPLES = 8;
|
||||||
|
static const flagtype KS_NEURONS_INI = 16;
|
||||||
|
|
||||||
|
extern flagtype state;
|
||||||
|
|
||||||
|
extern int tmax;
|
||||||
|
extern int samples;
|
||||||
|
extern int t, tmax, lpct, cells;
|
||||||
|
extern int gaussian;
|
||||||
|
|
||||||
|
extern int krad, kqty, kohrestrict;
|
||||||
|
extern int qpct;
|
||||||
|
extern int columns;
|
||||||
|
extern double dispersion_end_at;
|
||||||
|
extern int dispersion_count;
|
||||||
|
extern double learning_factor, distmul;
|
||||||
|
extern double ttpower;
|
||||||
|
extern int min_group, max_group, columns;
|
||||||
|
|
||||||
|
struct neuron {
|
||||||
|
kohvec net;
|
||||||
|
cell *where;
|
||||||
|
double udist;
|
||||||
|
int lpbak;
|
||||||
|
color_t col;
|
||||||
|
int allsamples, drawn_samples, csample, bestsample, max_group_here;
|
||||||
|
int debug;
|
||||||
|
neuron() { drawn_samples = allsamples = bestsample = 0; max_group_here = max_group; debug = 0; }
|
||||||
|
};
|
||||||
|
|
||||||
|
struct sample {
|
||||||
|
kohvec val;
|
||||||
|
string name;
|
||||||
|
};
|
||||||
|
|
||||||
|
inline void alloc(kohvec& k) { k.resize(columns); }
|
||||||
|
|
||||||
|
extern kohvec weights;
|
||||||
|
extern vector<sample> data;
|
||||||
|
extern vector<int> samples_to_show;
|
||||||
|
extern vector<neuron> net;
|
||||||
|
extern vector<string> colnames;
|
||||||
|
|
||||||
|
void initialize_neurons();
|
||||||
|
void initialize_neurons_initial();
|
||||||
|
void initialize_dispersion();
|
||||||
|
void initialize_samples_to_show();
|
||||||
|
void clear();
|
||||||
|
void create_neurons();
|
||||||
|
void analyze();
|
||||||
|
void step();
|
||||||
|
void initialize_rv();
|
||||||
|
void set_neuron_initial();
|
||||||
|
bool finished();
|
||||||
|
|
||||||
|
vector<cell*> gen_neuron_cells();
|
||||||
|
neuron& winner(int id);
|
||||||
|
}
|
||||||
|
|
||||||
|
namespace embeddings {
|
||||||
|
|
||||||
|
using kohonen::columns;
|
||||||
|
using kohonen::kohvec;
|
||||||
|
using kohonen::alloc;
|
||||||
|
|
||||||
|
enum embedding_type { eProjection, eNatural, eLandscape, eSignpost, eHypersian };
|
||||||
|
extern embedding_type etype;
|
||||||
|
void mark_signposts(bool full, const vector<cell*>& ac);
|
||||||
|
void generate_rug(int i, bool close);
|
||||||
|
void init_landscape(int dimensions);
|
||||||
|
|
||||||
|
extern map<cell*, hyperpoint> rug_coordinates;
|
||||||
|
extern void get_coordinates(kohvec& v, cell *c, cell *c0);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
@ -6,7 +6,6 @@
|
|||||||
#include "objmodels.cpp"
|
#include "objmodels.cpp"
|
||||||
#include "smoothcam.cpp"
|
#include "smoothcam.cpp"
|
||||||
|
|
||||||
#include "kohonen.cpp"
|
|
||||||
#include "staircase.cpp"
|
#include "staircase.cpp"
|
||||||
#include "banachtarski.cpp"
|
#include "banachtarski.cpp"
|
||||||
#include "pentagonal.cpp"
|
#include "pentagonal.cpp"
|
||||||
@ -55,5 +54,7 @@
|
|||||||
#endif
|
#endif
|
||||||
#include "highdim-demo.cpp"
|
#include "highdim-demo.cpp"
|
||||||
|
|
||||||
|
#include "kohonen.cpp"
|
||||||
|
#include "embeddings.cpp"
|
||||||
//#endif
|
//#endif
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user