
//[2012.04.20-1.목][전부수정!!!]{----------------------------------
//[2012.04.10.화] 에 처리된 것을 개념을 모두 수정하여 새로 만든다.
//}----------------------------------------------------------------


#ifndef str_heap_h
#define str_heap_h


struct STRHEAP
{
  //[2012.04.20-1.목][생성!!!]{--------------------------------------------------
  //문자열을 <new/delete> 로 관리하는 경우 알수 없는 오류가 발생하고
  //관리가 복잡해 지므로 별도의 문자열 관리 개체를 만든다.
  //
  //1) 문자열 크기에 제한이 없다.
  //2) 메모리 공간의 낭비가 없고 빈틈없이 공간을 이어서 관리한다.
  //3) 모든 문자열은 [관리번호] 로 접근한다.
  //4) 문자열 [저장소/목록] 이 구분돼 있고 각각 [위치(index)] 로 관리하므로
  //   저장소를 확대하기 위하여 [동적 재생성] 시에도 [위치(index)] 는 유지되므로
  //   어떤 상황에서도 같은 위치로 접근할수 있다.
  //5) 항상 한 덩어리의 공간을 관리하므로 [생성/삭제] 가 쉽다.
  //
  //향후 모든 문자열 관리시에 이 [문자열 공간] 을 사용하여 처리.
  //
  //[2012.05.09.수][추가!!!]-----------------------------------------------------
  //}----------------------------------------------------------------------------

  //[문자열 저장 공간 관련]
  //{
      //[공간]
      //{
          //[!]{------------------------------------------------------------
          //[동적생성] 되고 실제 [문자열묶음] 을 저장하는곳.
          //
          //                     <4>              <문자열공간크기>
          //문자열 묶음 :{ [문자열공간크기] [문자열공간('\0' 까지 저장)] }
          //
          //[목록] 에서는 이 [문자열 묶음] 위치(heap[] 상의 index) 를 관리.
          //}---------------------------------------------------------------

          char  *heap;

      //}

      //<heap[]> 공간 자체 전체 크기(생성/재생성 된 크기).
      int  hsize;

      //현재 저장할수 있는 위치(자체는 현재까지 저장된 총 크기와 같다).
      int  hp;

      //[재생성] 시 증가하는 크기.
      #define  d_STRHEAP_Heap_addSize    (512*1000)
      int  haddsize; //(기본값 : 512K)

  //}

  //[목록 관련]
  //{
      //[!]{-------------------------------------------------------------------
      //<heap> 상에 저장돼 있는 [문자열 묶음] 의 위치를 관리.
      //<heap> 와 별도로 부족한 경우 [동적 재생성] 되며,
      //<heap> 과는 달리 [정리] 되지 않으며 [등록/해제] 만 가능하다.
      //이는 [문자열 묶음] 을 참조하는 목록의 [번호(idnex)] 로 외부에서
      //[문자열] 에 접근하므로 절대 위치가 변경되어서는 안되기 때문.
      //
      //[문자열 묶음] 을 등록시에는 [해제(-1)] 상태인 [목록] 을 찾아
      //아무곳에나 기록하면 된다.
      //
      //더이상 [해제(-1)] 된 목록이 존재하지 않을 경우는 [재생성] 한다.
      //단, 이 경우라도 모든 내용 위치는 그대로 보존된다.
      //
      //[등록] : <heap[]> 상의 [위치(index)] 를 기록.
      //[해제] : -1(기본상태이고 다른 [문자열 묶음] 위치를 등록할수 있는 상태).
      //
      //[크기] 의 문제가 아니라, 더이상 목록을 등록할 [빈곳(해제된 곳)] 이
      //있는가 없는가만 중요.
      //}-----------------------------------------------------------------------

      //<heap[]> 상의 [문자열 묶음] 위치를 저장할 목록.
      //[등록/해제] 형태로 운영.
      //반드시 전체 공간을 <-1(해제상태)> 로 초기화 해야 한다.
      int  *list;

      //<list[]> 공간 자체 전체 크기(생성/재생성 된 크기).
      int   lsize;

      //[재생성] 시 증가하는 크기(목록 개수가 된다).
      //추가시 1024개의 문자열을 관리 할수 있도록 증설하면 충분하다.
      #define  d_STRHEAP_List_addSize    (1024)
      int   laddsize;

      //[2019.02.21.목][추가]{-----------------------------------------------------
      //[전체잧기] 기능 지원을 위한 것.
      //<true> 인 경우는 <STRHEAP_List_Add()> 내부적으로 [빈곳<-1>] 을 찾지 않고
      //무조건 <++> 형식으로 [등록번호] 를 증가시킨다.
      //단, 공간이 부족한 경우 재생성하는 것은 동일.
      //
      //이는 [전체찾기] 의 결과를 [전체찾기:Tree] 에 등록하는데 항목수가 100만개
      //정도에 이르는 경우도 발생하는데, 이때 <STRHEAP_List_Add()> 함수 안의
      //[빈곳 찾기] 부분에서 항상 처음부터 [빈곳] 을 찾는 방식이라 [엄청난] 시간
      //손실이 발생하기 때문이다.
      //
      //이를 방지하기 위하여 [전체찾기] 와 같이 [순서대로] && [대용량] 을 등록하는
      //경우는
      //1) 미리 [목록] 을 [찾은결과수] 만큼 [재생성] 한다(100만개일수도 있다).
      //
      //2) <lsNoSearch = true> 로 설정해 놓는다.
      //
      //3) 100만개 목록까지 그냥 ++ 형식으로 계속 추가만 하면된다.
      //
      //의 형식으로 처리한다.
      bool  lsNoSearch; //(false)
      int   lsCount;    //(0)
      //}--------------------------------------------------------------------------

  //}

  //[NULL 문자열 공간]
  //{
      //[2012.05.09.수][추가!!!]{-----------------------------------------
      //<STRHEAP_Str_Ptr()> 함수에서 <목록:-1> 인 경우는 이전에 <NULL> 을
      //직접 반환하였으나, 이 경우 [오류] 가 된다.
      //반드시 [문자열 위치] 를 반환해야 하므로 "" 을 반환한다.
      //이를 위하여 [반드시 존재하는 ""] 를 위한 공간을 만들어 준다.
      //
      //즉, "" 문자열을 제공하기 위한 전용 공간.
      //
      //<STRHEAP_Init()> 에서 [한번만] 초기화 하면 된다.
      //
      //이 공간은 [STRHEAP] 이 동적으로 [생성/삭제] 되어도 유지된다.
      //}-----------------------------------------------------------------

      char  nullStr[1]; //항상 '\0' 을 넣어 놓는다.

  //}

};

//[2012.05.09.수][완료!!!]
void __fastcall STRHEAP_Init(struct STRHEAP  *pStrHeap);

//[2012.05.07.월][완료!!!]
void __fastcall STRHEAP_Clear(struct STRHEAP  *pStrHeap);

//[2012.05.13.일][완료!!!]
void __fastcall STRHEAP_Delete(struct STRHEAP  *pStrHeap);

//[2012.04.20-1.목][완료!!!]
void __fastcall STRHEAP_Create(struct STRHEAP  *pStrHeap,
                               //<heap[]> 생성 크기.
                               int              pHeapSize,
                               //<list[]> 생성 크기.
                               int              pListSize);

//[2012.04.22.일][완료!!!]
void __fastcall STRHEAP_Str(struct STRHEAP  *pStrHeap,
                            //[재할당] 의 경우는 [목록번호] 는 전달받을수도 있다.
                            int             *prListIndex,
                            char            *pStr);

//[2012.04.20-1.목][완료!!!]
int __fastcall STRHEAP_Str_Add(struct STRHEAP  *pStrHeap,
                               char            *pStr);

//[2012.04.21.토][완료!!!]
void __fastcall STRHEAP_Str_Delete(struct STRHEAP  *pStrHeap,
                                   //삭제할 [문자열 목록] 번호(index).
                                   int              pListIndex);

//[2012.05.09.수][완료!!!]
char * __fastcall STRHEAP_Str_Ptr(struct STRHEAP  *pStrHeap,
                                  //[주소] 를 얻을 [문자열 목록] 번호(index).
                                  int              pListIndex);

//[내부적으로만 사용]
//{
    //[2012.04.20-1.목][완료!!!]
    //[2019.02.21.목][완료]
    //내부적으로만 <STRHEAP_Add()> 에서 사용된다.
    int __fastcall STRHEAP_List_Add(struct STRHEAP  *pStrHeap,
                                    //등록할 [문자열 묶음] 의 <heap[]> 상의 위치(index).
                                    int              pHeapIndex);

    //[2012.04.20-1.목][완료!!!]
    void __fastcall STRHEAP_Heap_ReSize(struct STRHEAP  *pStrHeap);

    //[2012.04.20-1.목][완료!!!]
    void __fastcall STRHEAP_List_ReSize(struct STRHEAP  *pStrHeap);

//}

//[특수용도]
//{
    //[2019.02.22.금][완료]
    void __fastcall STRHEAP_Heap_ReSizeX(struct STRHEAP  *pStrHeap,
                                         //[재생성] 시 추가할 크기.
                                         int              pAddSizeX);

    //[2019.02.21.목][완료]
    void __fastcall STRHEAP_List_ReSizeX(struct STRHEAP  *pStrHeap,
                                         //[재생성] 시 추가할 크기.
                                         int              pAddSizeX);

    //[2019.02.21.목][완료]
    void __fastcall STRHEAP_Set_List_NoSearch(struct STRHEAP  *pStrHeap,
                                              bool             pNoSearch,
                                              //시작 번호값.
                                              int              pStartCount);

    //[2019.02.22.금][완료]
    int __fastcall STRHEAP_Str_Search(struct STRHEAP  *pStrHeap,
                                      //[대/소] 문자 구분 여부(true:구분).
                                      bool             pCase,
                                      char            *pStr);

    //[2019.02.22.금][완료]
    int __fastcall STRHEAP_Get_Count(struct STRHEAP  *pStrHeap);

//}



#endif
