vgcore.*
prime.data
*.cfm
+*.CFM
all: $(TARGETS)
+compute: best.CFM
+
minimise: energy.o graph.o common.o mgraph.o minimise.o half.o
$(CXX) $(CXXFLAGS) -o $@ $^ $(LIBGSL)
ring.cfm: oldmoebius-converter prime.data /dev/null ../moebius/a.out
./$^ -o$@
+best.CFM: minimise sgtatham.cfm
+ ./$^ -iwip.cfm -o$@
+
view-%: view+%.o mgraph+%.o common.o
$(CC) $(CFLAGS) -o $@ $^ $(LIBGSL) -L/usr/X11R6/lib -lX11
clean:
rm -f prime.data $(TARGETS)
rm -f *.o *.new *.tmp *.rej *.orig core vgcore.* *~
- rm -f *.d
+ rm -f *.d *.cfm
realclean: clean
- rm -f best
+ rm -f *.CFM
%.d:
/*---------- main energy computation and subroutines ----------*/
double compute_energy(const struct Vertices *vs) {
+ static int bests_unprinted;
+
double energy;
int printing;
printing= printing_check(pr_cost,0);
- if (printing) printf("cost > energy |");
+ if (printing) printf("%15lld c>e |", evaluations);
COST(3e2, line_bending_cost(vs->a));
COST(1e3, edge_length_variation_cost(vs->a));
FILE *best_f;
int r;
- if (printing) printf(" BEST");
+ if (printing) {
+ printf(" BEST");
+ if (bests_unprinted) printf(" [%4d]",bests_unprinted);
+ bests_unprinted= 0;
+ } else {
+ bests_unprinted++;
+ }
- best_f= fopen(output_file_tmp,"wb"); if (!best_f) diee("fopen new out");
+ best_f= fopen(best_file_tmp,"wb"); if (!best_f) diee("fopen new out");
r= fwrite(vs->a,sizeof(vs->a),1,best_f); if (r!=1) diee("fwrite");
if (fclose(best_f)) diee("fclose new best");
- if (rename(output_file_tmp,output_file)) diee("rename install new best");
+ if (rename(best_file_tmp,best_file)) diee("rename install new best");
best_energy= energy;
}
flushoutput();
}
+ evaluations++;
return energy;
}
static void addcost(double *energy, double tweight, double tcost, int pr) {
double tenergy= tweight * tcost;
- if (pr) printf(" %# e x %# e > %# e* |", tcost, tweight, tenergy);
+ if (pr) printf(" %# e x %g > %# e* |", tcost, tweight, tenergy);
*energy += tenergy;
}
r= fstat(0,&stab); if (r) diee("fstat input to find length");
- if (!stab.st_size || stab.st_size % sizeof(double) ||
+ if (!stab.st_size || stab.st_size % (sizeof(double)*D3) ||
stab.st_size > INT_MAX)
fail("input file is not reasonable whole number of doubles\n");
- oldsz= stab.st_size / sizeof(double);
+ oldsz= stab.st_size / (sizeof(double)*D3);
for (shift=1;
- shift > XBITS+1 && shift > YBITS+1;
+ shift < XBITS+1 && shift < YBITS+1;
shift++) {
oldxbits= XBITS-1;
oldybits= YBITS-1;
oldx= 1<<oldxbits;
oldy= (1<<oldybits)-1;
+ fprintf(stderr,"sizeof(double)=%d XYBITS=%d,%d, XY=%d*%d=%d"
+ " oldsz=%d shift=%d oldxybits=%d,%d oldxy=%d*%d=%d\n",
+ (int)sizeof(double), XBITS,YBITS, X,Y,N,
+ oldsz,shift,oldxbits,oldybits,oldx,oldy,oldx*oldy);
if (oldx*oldy == oldsz) goto found;
}
fail("input file size cannot be interpolated to target file size\n");
found:
inc= 1<<shift;
+ fprintf(stderr,"inc=%d\n",inc);
}
static void read_input(void) {
- int x,y;
+ int x,y, ox,oy, v,ov;
- for (y=0; y<Y; y+=inc)
- for (x=0; x<X; x+=inc) {
+ for (oy=y=0; y<Y; oy++, y+=inc) {
+ fprintf(stderr, "y=%2d>%2d", oy,y);
+ for (ox=x=0; x<X; ox++, x+=inc) {
errno= 0;
- if (fread(all.a[(y << YSHIFT) | x], sizeof(double), D3, stdin) != D3)
- diee("read input");
+ ov= (oy << oldxbits) | ox;
+ v= (y << YSHIFT) | x;
+ fprintf(stderr, " 0%02o->0x%02x", ov, v);
+ if (fread(all.a[v], sizeof(double), D3, stdin) != D3)
+ diee("\nread input");
}
+ fputc('\n',stderr);
+ }
}
/* We use GSL's interpolation functions. Each xa array is simple
#include "half.h"
#include "minimise.h"
-const char *input_file, *output_file;
-char *output_file_tmp;
+const char *input_file, *best_file;
+char *best_file_tmp;
+long long evaluations;
static void printing_init(void);
-static gsl_multimin_fminimizer *minimiser;
-
static const double stop_epsilon= 1e-6;
+static gsl_multimin_fminimizer *minimiser;
+static const char *final_file;
+static char *final_file_tmp;
static double minfunc_f(const gsl_vector *x, void *params) {
struct Vertices vs;
return compute_energy(&vs);
}
+static void badusage(void) {
+ fputs("usage: minimise <input> [-i<intermediate>] -o<output\n",stderr);
+ exit(8);
+}
+
int main(int argc, const char *const *argv) {
gsl_multimin_function multimin_function;
double size;
gsl_vector initial_gsl, step_size_gsl;
int r, i;
- if (argc!=3 || argv[1][0]=='-' || strncmp(argv[2],"-o",2))
- { fputs("usage: minimise <input> -o<output\n",stderr); exit(8); }
+ if (argc==3) {
+ input_file= argv[1];
+ if (strncmp(argv[2],"-o",2)) badusage(); best_file= argv[2]+2;
+ final_file= 0;
+ } else if (argc==4) {
+ input_file= argv[1];
+ if (strncmp(argv[2],"-i",2)) badusage(); best_file= argv[2]+2;
+ if (strncmp(argv[3],"-o",2)) badusage(); final_file= argv[3]+2;
+ } else {
+ badusage();
+ }
+ if (argv[1][0]=='-') badusage();
- input_file= argv[1];
- output_file= argv[2]+2;
- if (asprintf(&output_file_tmp,"%s.new",output_file) <= 0) diee("asprintf");
+ if (asprintf(&best_file_tmp,"%s.new",best_file) <= 0) diee("asprintf");
+ if (final_file)
+ if (asprintf(&final_file_tmp,"%s.new",final_file) <= 0) diee("asprintf");
graph_layout_prepare();
printing_init();
size= gsl_multimin_fminimizer_size(minimiser);
r= gsl_multimin_test_size(size, stop_epsilon);
- if (printing_check(pr_size,155))
- printf("size %# e, r=%d\n", size, r);
+ if (printing_check(pr_size,215))
+ printf("r=%2d, size %# e\n", r, size);
flushoutput();
if (r==GSL_SUCCESS) break;
assert(r==GSL_CONTINUE);
}
+
+ if (final_file) {
+ if (unlink(final_file_tmp) && errno != ENOENT) diee("unlink final .tmp");
+ if (link(best_file,final_file_tmp)) diee("link final .tmp");
+ if (rename(final_file_tmp,final_file)) diee("install final");
+ }
+ printf("FINISHED (%lld evaluations)\n",evaluations);
+
return 0;
}
print_todo &= ~bits;
sigprocmask(SIG_UNBLOCK,&print_alarmset,0);
+ printf("%*s",indent,"");
sk= skipped[which];
- if (sk) printf("%*s[%4d] ",indent,"", sk);
- else printf(" ");
+ if (sk) printf("[%4d] ",sk);
+ else printf(" ");
skipped[which]= 0;
return 1;
double edge_length_variation_cost(const Vertices vertices);
double rim_proximity_cost(const Vertices vertices);
-extern const char *input_file, *output_file;
-extern char *output_file_tmp;
+extern const char *input_file, *best_file;
+extern char *best_file_tmp;
+extern long long evaluations;
enum printing_instance { pr_cost, pr_size, pr__max };
int printing_check(enum printing_instance, int indent);