바람이 머문 언덕

template 기능과 함수 포인트를 사용한 Double list 본문

컴퓨터 IT/C++ 언어

template 기능과 함수 포인트를 사용한 Double list

알 수 없는 사용자 2009. 11. 26. 00:01
반응형

//  리스트는 많이 사용하는 데이터 구조라 template 기능과 함수 포인트를 이용해서 만든 더블 리스트 입니다.
// 비교 함수와 노드 삭제 함수를 클래스 만들어서 클래서 생성시 전달 해주어야 합니다.
// template 기능을 사용하는 함수는 라이블리 파일로 만들 수 없고 소스 형태로 포함 되어야 합니다.

//예)   struct data{ int day;  char *memo;  long money; long balance;  unsigned long code; } ;
//       struct node{ node *prev; data *dt; node *next; } ;

//    static int cmpdata(data* n, data* d)   
//    { return (n->day==d->day) ? 0 : (n->day<d->day) ? -1 : 1; } 
 
//    static void delnode( node* temp)
//    { if(temp->dt->memo) delete temp->dt->memo; delete temp->dt; delete temp; }

//       Ndblist<node, data> *dblist;
//       dblist= new Ndblist<node, data> (cmpnode, cmpdata);

// 더블 리스트 헤드 파일과 윈도우 API 함수로 만든 금전 출납부 소스 파일 입니다.

ndblist.h

mutiawjs.zip



#include <stdio.h>
#include <string.h>
#include <math.h>
#include <stdlib.h>
 
typedef unsigned int        UINT;

template<class N,class D> class Ndblist 
{
     public:
        int ( *ftncmp)(D *,D * );      // 비교 함수 포인트
        Ndblist( int ( *fcmp)(D *,D * ), void ( *ftdel)(N *)) ;   
        ~Ndblist( ) { alldel();          }
       void Setcmp(int (*fcmp)(D *,D *, int ))    { ftncmp=fcmp;       }
       unsigned int count()   { return icount;     } 
       N *top()                     { return topnode;    }
       N *bottom()                 { return btmnode;    }
       /* N *makenode(D *dt)
         {
             N *istnode=new N;
             if(istnode) istnode->dt=dt;
             return istnode;
         }*/
      N *add(D *dt);             //추가
      void del( N *temp );      //노드 삭제
      void alldel();                //리스트 삭제
      void unnode( N *temp );     //노드 분리
      // void pteorder(N *temp);  //전위순회
      // void inorder(N *temp);    //중위 순회
     void istprev( N *po, N *ist ); //po앞에   ist 삽입
     void istnext( N *po, N *ist ); //po뒤에    ist 삽입
     N *insertst(N * /*시작 포인터*/, D * /* 삽입 데이터*/, UINT &ic, N *istnode=NULL);     //순차 삽입
     int insertsh(N *&, D * , UINT &ic);     //순차 검색
     //void chposition(N *mv,N *po,int i=1);
   protected:
      /*  void delnode( N *temp)
         {
              //delete[] temp->dt;delete[] temp->dt; delete temp;
          }*/
      N *btmnode, *topnode;  
      unsigned int icount;           //현 항목 위치와 갯수
      void ( *ftndel)(N *);            // 노드 삭제 함수 포인트
};

template<class N,class D> Ndblist<N,D>::Ndblist(int ( *fcmp)(D *,D * ), void ( *ftdel)(N *))
{
      btmnode=topnode=NULL; icount=0; ftncmp=fcmp; ftndel=ftdel;
}

template<class N,class D>N *Ndblist<N,D>::add(D *dt)
{
     //N *istnode=
     N *istnode=new N;
     //   if(istnode) istnode->dt=dt;//makenode(dt); 
    if(istnode)
    {
        istnode->dt=dt;
       if(btmnode)
       {
           istnode->prev=topnode; istnode->next=topnode->next;
           topnode->next=istnode;
       }
       else
      {
           btmnode=istnode;
           istnode->prev=istnode->next=NULL;
      }
      topnode=istnode; ++icount;
   }  
   return istnode;
}
 
template<class N,class D> void Ndblist<N,D>::istprev( N *po, N *ist )
{
     ist->prev=po->prev; ist->next=po; icount++;
     (po->prev) ? po->prev->next=ist : btmnode=ist;
     po->prev=ist;
}

template<class N,class D> void Ndblist<N,D>::istnext( N *po, N *ist)
{
     ist->prev=po; ist->next=po->next; icount++;
    (po->next) ? po->next->prev=ist : topnode=ist;
    po->next=ist;
}

template<class N,class D> void Ndblist<N,D>::unnode( N *temp )//
{
     icount--;
     if(temp->next) temp->next->prev=temp->prev;
     else           topnode=temp->prev;
     (temp->prev) ? temp->prev->next=temp->next : btmnode=temp->next;
}

template<class N,class D> void Ndblist<N,D>::del( N *temp )//
{
      unnode(temp ); (*ftndel)(temp);
}

template<class N,class D> void Ndblist<N,D>::alldel()//
{
     N *temp=btmnode;
     while(temp)
    {
         btmnode=temp->next;
         (*ftndel)(temp);
         temp=btmnode;
    }
    icount=0;
    btmnode=topnode=NULL;
}

template<class N,class D> N *Ndblist<N,D>::insertst( N *po, D *dt , UINT &ic, N *istnode)
{
      // ic=  갯수  i 같은 것이 있을 때 k 비교,
      int s;
      if(!istnode) istnode=new N;//makenode(dt);
      if(istnode)
     {
          istnode->dt=dt;
          if(btmnode)
          {
               if(po==NULL) { po=topnode; ic=icount; }
              s=insertsh(po, dt, ic);
              if(s==-1) {  istprev(po, istnode ); }
              else //if((s==1) || (s==0))  }// 크거나 같은 것이 있으면
              { 
                     ic++; istnext(po, istnode );
               }
         }
         else
        {
               btmnode=topnode=istnode;
               ic=icount=1; //s=0;
               istnode->prev=istnode->next=NULL;
        }
    }
    return istnode;
}

template<class N,class D> int Ndblist<N,D>::insertsh(N *&temp, D *dt, UINT &ic) // 순차 검색  ?
{
       int  s=0, i=0;
       while(temp)
       {
           i=(*ftncmp)(dt, temp->dt); 
           if(i==-1)       // 작으면
          {
               if((s>0) || (!temp->prev)) break;
               else
               {
                    s=-1;  ic--; temp=temp->prev; 
               }
         }
         else if(i==1)  // 크면
         {
              if((s<0) || (!temp->next)) break;
              else {  s=1;  ic++; temp=temp->next;  }
        }
        else  break;  //(i == 0)   같으면 
    }
    return i;
}