Main Page   Data Structures   File List   Data Fields   Globals  

lvlslice.c

Go to the documentation of this file.
00001 #include        "sadie.h"
00002 
00003 /*-Copyright Information------------------------------------------------------*/
00004 /* Copyright (c) 1988 by the University of Arizona Digital Image Analysis Lab */
00005 /*----------------------------------------------------------------------------*/
00006 /*-General Information--------------------------------------------------------*/
00007 /*                                                                            */
00008 /*   This function performs a level-slice classification on an image.         */
00009 /*   Pixels lying within two or more boxes in feature space are assigned      */
00010 /*   by the nearest-mean algorithm.                                           */
00011 /*                                                                            */
00012 /*----------------------------------------------------------------------------*/
00013 /*-Interface Information------------------------------------------------------*/
00014 void LVLSLICE (
00015 IMAGE *in,      /*  I   Pointer to the input image.                           */
00016 PIXEL *grng,    /*  I   Matrix[nlev][nbnd][2], containing class boundaries.   */
00017 short nlev,     /*  I   Number of classes                                     */
00018                 /*      (and number of graylevels in the output image).       */
00019 IMAGE **out     /*  O   Address of a pointer to the output image.             */
00020                 /*      The input image may be overwritten (out = &in).       */
00021 /*----------------------------------------------------------------------------*/
00022 ) { register short i, j, k, l, index, count, assign, class;
00023     char  msg[SLEN];
00024     PIXEL *center=0, dnew, dold;
00025 
00026     if (TIMES) TIMING(T_LVLSLICE);
00027     if (NAMES) {
00028         MESSAGE('I',"");
00029         MESSAGE('I',"LVLSLICE");
00030         MESSAGE('I',"");
00031         sprintf(msg," Input image:         %s",in->text);
00032         MESSAGE('I',msg);
00033         sprintf(msg," Number of classes:   %d",nlev);
00034         MESSAGE('I',msg);
00035         sprintf(msg,"       ");
00036         for (i=0; i<in->nbnd; i++) {
00037             sprintf(msg+strlen(msg),"          Band %-11d",i+1);
00038         }
00039         MESSAGE('I',msg);
00040         sprintf(msg," Class");
00041         for (i=0; i<in->nbnd; i++) {
00042             sprintf(msg+strlen(msg),"      Min         Max     ");
00043         }
00044         MESSAGE('I',msg);
00045         for (i=0; i<nlev; i++) {
00046             sprintf(msg," %3d ",i+1);
00047             for (j=0; j<in->nbnd; j++) {
00048                 sprintf(msg+strlen(msg),"%14.4e%12.4e",grng[(i*in->nbnd+j)*2+0],grng[(i*in->nbnd+j)*2+1]);
00049             }
00050             MESSAGE('I',msg);
00051         }
00052         MESSAGE('I'," ...............");
00053     }
00054 
00055     /* check input */
00056     if (!CHECKIMG(in)) {
00057         MESSAGE('E'," Can't identify image.");
00058         goto the_end;
00059     } else if (nlev <= 0) {
00060         MESSAGE('E'," Number of classes must be greater than zero.");
00061         goto the_end;
00062     }
00063 
00064     /* create image of appropriate size */
00065     if (!CHECKIMG(*out)) GETMEM(1,in->nlin,in->npix,out);
00066     if (!*out) goto the_end;
00067 
00068     /* allocate space for center array */
00069     if (!(center=(PIXEL *)malloc(nlev*in->nbnd*sizeof(PIXEL)))) {
00070         MESSAGE('E'," Memory request failed.");
00071         goto the_end;
00072     }
00073 
00074     /* compute center coordinates for each class  */
00075     for (j=i=0; i<nlev*in->nbnd; i++) {
00076         center[i] = (grng[j++]+grng[j++])/2.0;
00077     }
00078 
00079     /* perform a level slice classification */
00080     for (j=0; j<in->nlin; j++) {
00081         for (k=0; k<in->npix; k++) {
00082             for (assign=index=class=l=0; l<nlev; l++) {
00083                 for (index=l*in->nbnd*2,count=i=0; i<in->nbnd; i++) {
00084                     if (grng[index++] <= in->data[i][j][k]  &&  in->data[i][j][k] <= grng[index++]) {
00085                         count += 1;
00086                     } else {
00087                         break;
00088                     }
00089                 }
00090                 if (count == in->nbnd) {
00091                     if (assign == 0) {
00092                         class  = l + 1;
00093                         assign = 1;
00094                     } else /* calculate distance to competing classes */ {
00095                         for (dold=dnew=0.0,i=0; i<in->nbnd; i++) {
00096                             dold += (in->data[i][j][k]-center[(class-1)*in->nbnd+i])*(in->data[i][j][k]-center[(class-1)*in->nbnd+i]);
00097                             dnew += (in->data[i][j][k]-center[l*in->nbnd+i])*(in->data[i][j][k]-center[l*in->nbnd+i]);
00098                         }
00099                         if (dnew < dold) class = l + 1;
00100                     }
00101                 }
00102             }
00103             (*out)->data[0][j][k] = (PIXEL)class;
00104         }
00105     }
00106 
00107     the_end:
00108     if (center) free(center);
00109     if (TIMES)  TIMING(T_EXIT);
00110 }

Generated on Wed Apr 9 08:56:08 2003 for TREES by doxygen1.2.14 written by Dimitri van Heesch, © 1997-2002