/*******************************************************\
* 							*
*              @(#)hills.c	1/13/89			*
*	Author:       Tony Plate			*
*	Copyright (C) 1989 Tony Plate			*
*	This program may be freely distributed and	*
*	used, provided that this copyright notice is	*
*	retained intact.  There is no warranty with	*
*	this software.					*
* 							*
\*******************************************************/
#include <stdio.h>
#define DB(X) 
/*
 * hills - toy program - generate a matrix with hills - randomly
 * two arguments, edge of matrix & number of hills
 */

int max(int x ,
        int y ) 
{ if (x > y) return x; else return y; }
int min(int x ,
        int y ) 
{ if (x < y) return x; else return y; }
int iab(int x ) 
{ if (x >= 0) return x; else return -x; }

int inbounds(int *array ,
             int d ,
             int x ,
             int y )

{
  DB( printf("[%2d %2d ",x,y); )
  if ((x<0) || (x>=d) || (y<0) || (y>=d)) {
    DB( printf("--] "); )
    return 0;
  } else {
    DB( printf("%2d] ",array[x*d + y]); )
    return array[x*d + y];
  }
}

#define srandom srand
#define random rand

int main(int argc ,
         char *argv[] )

{
  int d,n_hills,*array,height,i,j,x,y,corrected,new;
  height = 5;
  if (argc < 3) {
    fprintf(stderr,"usage: %s size n-hills [height [seed]]\n",argv[0]);
    exit(1);
  }
  d = atoi(argv[1]);
  n_hills = atoi(argv[2]);
  if (argc > 3) height = atoi(argv[3]);
  srandom(getpid());
  if (argc > 3) srandom(atoi(argv[4]));
  array = (int*)calloc(sizeof(int),d * d);
  for (i=0;i<d;i++)
    for (j=0;j<d;j++)
      array[i*d+j]=0;
  for (;n_hills > 0;n_hills--) {
    x = random() % d;
    y = random() % d;
    array[x*d+y]=height;
    /*
    for (i=max(x-height,0);i<=min(x+height,d);i++)
      for (j=max(y-height,0);j<=min(x+height,d);j++) {
	array[i*d+j] = max(array[i*d+j],min(height-iab(i-x),height-iab(j-y)));
      }
    */
  }
  do {
    corrected = 0;
    for (i=0;i<d;i++)
      for (j=0;j<d;j++) {
	DB( printf("Looking at [%2d %2d %2d]: ",i,j,array[i*d+j]); )
	new = max(inbounds(array,d,i,j),
		  max(inbounds(array,d,i-1,j-1),
		  max(inbounds(array,d,i-1,j  ),
		  max(inbounds(array,d,i-1,j+1),
		  max(inbounds(array,d,i  ,j-1),
		  max(inbounds(array,d,i  ,j+1),
		  max(inbounds(array,d,i+1,j-1),
		  max(inbounds(array,d,i+1,j  ),
		  inbounds(array,d,i+1,j+1))))))))-1);
	DB( printf("new = %d\n",new); )
	if (array[i*d+j]!=new) {
	  corrected++;
	  array[i*d+j]=new;
	}
      }
  } while (corrected);
  array[0]=height+1;
  printf("%d %d\n",d,d);
  for (i=0;i<d;i++) {
    for (j=0;j<d;j++)
      printf(" %3d",array[i*d+j]);
    printf("\n");
  }
}
