⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 lvq_run.c

📁 face recognition test source code
💻 C
📖 第 1 页 / 共 3 页
字号:
/************************************************************************
 *                                                                      *
 *  Program package 'lvq_pak':                                          *
 *                                                                      *
 *  lvq_run.c                                                           *
 *  - user interface to lvq_pak                                         *
 *                                                                      *
 *  Version 3.0                                                         *
 *  Date: 1 Mar 1995                                                    *
 *                                                                      *
 *  NOTE: This program package is copyrighted in the sense that it      *
 *  may be used for scientific purposes. The package as a whole, or     *
 *  parts thereof, cannot be included or used in any commercial         *
 *  application without written permission granted by its producents.   *
 *  No programs contained in this package may be copied for commercial  *
 *  distribution.                                                       *
 *                                                                      *
 *  All comments  concerning this program package may be sent to the    *
 *  e-mail address 'lvq@cochlea.hut.fi'.                                *
 *                                                                      *
 ************************************************************************/

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#ifndef max
#define max(x,y) ((x)<(y) ? (y):(x))
#endif

#ifdef MSDOS 
#include <sys\\stat.h>
#else
#include <sys/types.h>
#include <sys/stat.h>
#endif
#include "lvq_pak.h"
#include "datafile.h"
#include "labels.h"

/*---------------------------------------------------------------------------*/
#define R_OK 4
#define W_OK 2
#define F_OK 0

#define BEL 7
#define FLEN 80
#define CMD_LEN 160
#define SAVED_HISTORY	20
#define MAX_NUM_CLASSIFIERS 10

/*---------------------------------------------------------------------------*/

#define DEFAULT_LVQ1_ALPHA	0.03
#define DEFAULT_LVQ2_ALPHA	0.03
#define DEFAULT_LVQ3_ALPHA	0.03

enum e_lvq_init   { NONE=0, EVEN, PROP};
enum e_lvq_status { NOTHING=0, INIT, TRAIN, RETRAIN};



struct classifier {
  char	din[FLEN];
  int	notv;
  char	cout[FLEN];
  char	tdin[FLEN];
  int	noc;
  int	init_opt;
  int	lvq_status;
  long	rlen, totrlen;
  int	rt_lvq_type;
  long	rt_rlen;
  float	rt_alpha;
  float	rt_win;
  float rt_epsilon;
  float	accuracy;
  char	*history[SAVED_HISTORY];
  int	hist_i;
  int	train_hist_bgn;
  int	retrain_hist_bgn;
};

typedef struct classifier CLASSIFIER;


/*---------------------------------------------------------------------------*/
char
  *init_ext=	".ini",	
  *train_ext=	".cod",	
  *retrain_ext=	".lvq",	
  *class_ext=	".cfo",	
  *acc_ext=	".acc",
  *alpha_ext=	".lra",
  *init_alpha_ext=".lrs",
  *train_alpha_ext=".lrt",
  *log_ext=	".log";	

char *prog_dir;

#ifdef MSDOS 
char
  *type_cmd=	"type",
  *copy_cmd=	"copy";
#else /* UNIX */
char	
  *type_cmd=	"cat",
  *copy_cmd=	"cp";
#endif


char *sep = "\n\
==============================================================================\
\n";

char *introMsg0 = "\n\
\nThis program acts as a very simple interactive interface to the lvq_pak.\
\nTo run this program, you must have a training data file in the format\
\nexplained in the document. Preferably, you ought to have independent test\
\ndata to evaluate the performance, too. In addition, you must have an idea\
\nof how many codebook vectors you wish to use. This number depends on the";
char *introMsg1 = "\
\ndimensionality of the training data, on the number of classes you\
\nhave and on the amount of training data available.\
\nThe program suggests default values for most of the parameters. We suggest\
\nthat you use them initially. To select the default value in question, just\
\npress enter.\
\n";




/*---------------Routines related to history handling------------------------*/

void fix_init_history(CLASSIFIER *c) {c->train_hist_bgn = c->hist_i;}
     
void fix_train_history(CLASSIFIER *c) {c->retrain_hist_bgn = c->hist_i;}
     
void decrease_lvq_status(CLASSIFIER *c, int newstatus) 
{
  char l[CMD_LEN];
  int i;
  
  if (newstatus < c->lvq_status) {
    switch (newstatus) {
    case NOTHING:
      for (i=0; i<c->hist_i; i++) free(c->history[i]);
      c->hist_i = c->train_hist_bgn = c->retrain_hist_bgn = 0;
      sprintf(l,"%s%s",c->cout,alpha_ext); remove(l);
      break;
    case INIT:
      for (i=c->train_hist_bgn; i<c->hist_i; i++) free(c->history[i]);
      c->hist_i = c->train_hist_bgn;
      c->retrain_hist_bgn = 0;
      break;
    case TRAIN:
      for (i=c->retrain_hist_bgn; i<c->hist_i; i++) free(c->history[i]);
      c->hist_i = c->retrain_hist_bgn;
      break;
    default:
      fprintf(stdout,"\nERROR: Cannot decrease status!\n");
      break;
    }
    c->lvq_status = newstatus;
  }
}


char *dup_history(char *str)
{
  return( (char *)memcpy( (char *)malloc(max(CMD_LEN,strlen(str)+1)), 
			 str, 
			 strlen(str)+1 ));	
}


char *repl_history(char *inwhere, char *what, char *bywhat) 
     /* Replaces all occurrences of " what." by " bywhat." 
	in string "inwhere". Assumes there is enough space. */
{
  int i,j,len,lwhatlen,lbywhatlen;
  char lwhat[FLEN], lbywhat[FLEN], duplicate[CMD_LEN];
  
  len = strlen(inwhere);
  lwhat[0]=lbywhat[0]=' ';
  strcpy( lwhat+1, what );
  strcpy( lbywhat+1, bywhat );
  strcat( lwhat, ".");
  strcat( lbywhat, ".");
  lwhatlen = strlen(lwhat);
  lbywhatlen = strlen(lbywhat);
  strcpy(duplicate,inwhere);
  
  for (i=j=0; i<len;) {
    if (strncmp(&duplicate[i],lwhat,lwhatlen)==0) {
      memcpy( &inwhere[j], lbywhat, lbywhatlen);
      j += lbywhatlen;
      i += lwhatlen;
    } else  
      inwhere[j++] = duplicate[i++];
  }
  inwhere[j] = '\0';
  return(inwhere);
}


void copy_history(CLASSIFIER *c1, CLASSIFIER *c2) 
     /* copies history of c2 to c1 and replaces filenames */
{
  int i;
  for (i=0; i<c2->hist_i; i++) c1->history[i] = 
    repl_history( dup_history(c2->history[i]), c2->cout, c1->cout);
}



/*----------------------Some assisting routines------------------------------*/

void systemd(char *cmd)
{
  fprintf(stdout,">>%s\n",cmd); 
  fflush(stdout);
  system( cmd );
}


void systemh(char *cmd, CLASSIFIER *c)
{
  systemd( cmd );
  c->history[c->hist_i++] = dup_history(cmd);
}


void getsb(char *line)
{
  if (!silent(-1))
    putchar(BEL);
  fgets(line, CMD_LEN, stdin);
  if (line[strlen(line)-1] == '\n')
    line[strlen(line)-1] = (char) NULL;
}	

int faccess( char *name, int amode)
{
  int err;
  struct stat s;
  err = stat( name, &s );
  if (err == -1) return(-1); else
  switch (amode) {
	case R_OK:
	case F_OK:
		if (s.st_mode & S_IREAD) return(0); else return(-1);
	case W_OK:
		if (s.st_mode & S_IWRITE) return(0); else return(-1);
	default:
		return(-1);
  }
}


int check_filename( char *name, int amode)
{
  int ok = 1;
  char l[CMD_LEN];
  
  switch (amode) {
  case R_OK:
    ok = (faccess(name,amode) == 0);
    if (!ok) {
      sprintf(l,"\n Cannot read file %s\n",name);
      perror(l);
    }
    break;
  case W_OK:
    if ( faccess(name,F_OK) == 0) {
      fprintf(stdout,"\n File %s already exists",name);
      fprintf(stdout,"\n Enter y to overwrite: ");
      getsb(l);
      if (*l == 'y') {
	ok = (faccess(name,amode) == 0);
	if (!ok) {
	  sprintf(l,"\n Cannot write to file %s\n",name);
	  perror(l);
	} else {
	  ok = 2;
	}
      } else {
	ok=0;
      }
    } else {
      FILE *f;
      if ( (f=fopen(name,"w"))==NULL) {
	fprintf(stdout,"\n Cannot create file %s \n",name);
	ok=0;
      } else {
	fclose(f);
	remove(name);
	ok=1;
      }
    }
    break;
  default:
    fprintf(stdout,"\nERROR: Illegal file access mode %d!\n",amode);
    exit(-1);
  }
  return (ok);
}



void remove_classifier_files( char *cname )
{
  char l[CMD_LEN];
  sprintf(l,"%s%s",cname,init_ext);remove(l); 
  sprintf(l,"%s%s",cname,train_ext);remove(l);
  sprintf(l,"%s%s",cname,retrain_ext);remove(l); 
  sprintf(l,"%s%s",cname,class_ext);remove(l);
  sprintf(l,"%s%s",cname,acc_ext);remove(l); 
  sprintf(l,"%s%s",cname,alpha_ext);remove(l);
  sprintf(l,"%s%s",cname,init_alpha_ext);remove(l); 
  sprintf(l,"%s%s",cname,train_alpha_ext);remove(l); 
  sprintf(l,"%s%s",cname,log_ext);remove(l);
}



void copy_classifier_files( char *existing, char *new )
{
  char l[CMD_LEN];
  sprintf(l,"%s %s%s %s%s",copy_cmd, existing,init_ext, new,init_ext);
  system(l);
  sprintf(l,"%s %s%s %s%s",copy_cmd, existing,train_ext, new,train_ext);
  system(l);
  sprintf(l,"%s %s%s %s%s",copy_cmd, existing,class_ext, new,class_ext);
  system(l);
  sprintf(l,"%s %s%s %s%s",copy_cmd, existing,acc_ext, new,acc_ext);
  system(l);
  sprintf( l, "%s%s", existing,retrain_ext);
  if ( faccess(l, R_OK) == 0) {
	sprintf(l,"%s %s%s %s%s",copy_cmd, existing,retrain_ext, new,retrain_ext);
	system(l);
  }
  sprintf( l, "%s%s", existing,alpha_ext);
  if ( faccess(l, R_OK) == 0) {
	sprintf(l,"%s %s%s %s%s",copy_cmd, existing,alpha_ext, new,alpha_ext);
	system(l);
  }
  sprintf( l, "%s%s", existing,init_alpha_ext);
  if ( faccess(l, R_OK) == 0) {
	sprintf(l,"%s %s%s %s%s",copy_cmd, existing,init_alpha_ext, new,init_alpha_ext);
	system(l);
  }
  sprintf( l, "%s%s", existing,train_alpha_ext);
  if ( faccess(l, R_OK) == 0) {
	sprintf(l,"%s %s%s %s%s",copy_cmd, existing,train_alpha_ext, new,train_alpha_ext);
	system(l);
  }
}


/*---------------------------------------------------------------------------*/

void estimate_needed_codevectors
  (char *in_code_file, int *noc, int *notv)
{
  struct data_entry *e;
  struct hit_entry *h;
  struct hitlist *classes;
  eptr p;
  int nol = 0, sum = 0, retval;
  struct entries *codes;
  
  if ((codes = open_entries(in_code_file)) == NULL)
    {
      fprintf(stderr, "Can't open data file '%s'\n", in_code_file);
      exit(1);
    }

  if ((classes = new_hitlist()) == NULL)
    return; /* error */

  for (e = rewind_entries(codes, &p); e != NULL; e = next_entry(&p))
    add_hit(classes, get_entry_label(e));

  fprintf(stdout,"\n\n The dimensionality of the training data in file %s is %d.",
	  in_code_file, codes->dimension);
  for (h = classes->head; h != NULL; h = h->next)
    {
      fprintf(stdout, "In class %s are %d units\n",
	      find_conv_to_lab(h->label), h->freq);
      sum += h->freq;
      nol++;
    }

  fprintf(stdout," The total number of training vectors is %d.\n\n",sum);
  retval = 0.4 * nol*( nol-1 + codes->dimension/2);
  if (retval > sum) retval = sum;
  close_entries(codes);
  
  *noc = retval;
  *notv = sum;
}




/*--------Read parameters from user for the LVQ_PAK programs-----------------*/

void default_classifier(CLASSIFIER *c)
{
  c->din[0] = c->cout[0] = c->tdin[0] = '\0';
  c->noc = c->notv = 0;
  c->init_opt = EVEN;
  c->lvq_status = NOTHING;
  c->rt_lvq_type = 1;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -