commit 2025-09-02 13:32 refine Replace() in ZCppMain/ZtCStringEx.H

This commit is contained in:
2025-09-02 13:32:40 +09:00
parent 660a66c58b
commit af3cf17663
2 changed files with 233 additions and 208 deletions

View File

@ -48,10 +48,10 @@ namespace ZNsMain
ZCStringStd& operator=(const TypeBase& rhs)*/
template<typename TPosList> void FindPosToList
template<typename TPosList> void FindPosToList /////////////
(
const char* APC_SearchData, TypeLength AL_SearchLen,
TPosList& ARR_CPosList , TypeLength AL_Offset=0
TPosList& ARR_CPosList, TypeCPChar APC_SearchData,
TypeLength AL_SearchLen, TypeLength AL_Offset=0
)
/*########################################################*/
{
@ -83,10 +83,10 @@ namespace ZNsMain
}
/*::::::::::::::::::::::::::::::::::::::::::::::::::::*/
}/*
template<typename TPosList> void FindPosToList
template<typename TPosList> void FindPosToList /////////////
(
const char* APC_SearchData, TypeLength AL_SearchLen,
TPosList& ARR_CPosList , TypeLength AL_Offset=0
TPosList& ARR_CPosList, TypeCPChar APC_SearchData,
TypeLength AL_SearchLen, TypeLength AL_Offset=0
)
##########################################################*/
@ -252,8 +252,8 @@ namespace ZNsMain
ZCStringStd& Replace /*####################################################*/
(
TypeCPChar APC_Search , TypeLength AL_Search ,
TypeCPChar APC_Replace, TypeLength AL_Replace, TypeLength AL_Offset=0
TypeCPChar APC_Search, TypeCPChar APC_Replace,
TypeLength AL_Search , TypeLength AL_Replace , TypeLength AL_Offset=0
)
/*#########################################################################*/
{
@ -263,7 +263,7 @@ namespace ZNsMain
ZtCList<TypeLength> VO_CPosCList; FindPosToList
(
APC_Search, AL_Search, RR(VO_CPosCList), AL_Offset
RR(VO_CPosCList), APC_Search, AL_Search, AL_Offset
);
/*////////////////////////////////////////////*/
@ -276,8 +276,8 @@ namespace ZNsMain
}/*
ZCStringStd& Replace /*######################################################
(
TypeCPChar APC_Search , TypeLength AL_Search ,
TypeCPChar APC_Replace, TypeLength AL_Replace, TypeLength AL_Offset=0
TypeCPChar APC_Search, TypeCPChar APC_Replace,
TypeLength AL_Search , TypeLength AL_Replace , TypeLength AL_Offset=0
)
###########################################################################*/

View File

@ -36,6 +36,7 @@ namespace ZNsMain
typedef long TypeLength;
typedef TTypCh TypeData ;
typedef TTypCh TypeChar ;
typedef TTypCh* TypePChar ;
typedef const TTypCh TypeCharC ;
typedef const TTypCh* TypeCharCP;
typedef const TTypCh* TypeCPChar;
@ -142,6 +143,7 @@ namespace ZNsMain
{
public:
typedef TLength TypeLong ;
typedef TLength TypeSize ;
typedef TLength TypeLength;
typedef TTypCh TypeChar ;
public:
@ -271,6 +273,7 @@ namespace ZNsMain
typedef const TTypCh TypeCharC ;
typedef const TTypCh* TypeCharCP ;
typedef const TTypCh* TypeCPChar ;
typedef TTypCh* TypePChar ;
typedef TTypeString ZCTypeString;
typedef ZtCStringBase ZCStringBase;
public:
@ -279,6 +282,7 @@ namespace ZNsMain
typedef typename ZCTypeString::ZCTypeChars ZCTypeChars ;
typedef typename ZCTypeString::ZCMainChars ZCMainChars ;
typedef typename ZCTypeString::TypeLong TypeLong ;
typedef typename ZCTypeString::TypeLong TypeSize ;
typedef typename ZCTypeString::TypeLong TypeLength ;
public:
typedef typename ZCTypeChars ::TypeChar TypeChar ; // TTypCh 과 같은 형이어야 한다.
@ -310,67 +314,212 @@ namespace ZNsMain
public:
template<typename TSearchInfoList> void MakeInfoList
template<typename TPosList> void FindPosToList /////////////
(
TypeCharC* APC_Search ,
TypeLength AL_SearchLen,
TypeLength AL_StartPos ,
TSearchInfoList& ARR_InfoList
TPosList& ARR_CPosList, TypeCPChar APC_SearchData,
TypeLength AL_SearchLen, TypeLength AL_Offset=0
)
////////////////////////////////////////////////////
/*########################################################*/
{
typedef typename
TSearchInfoList::TypeData ZCSearchInfo;
// TPosList : ZNsMain::ZtCList<TypeLength> etc
if(ml_UseLen <1 || AL_SearchLen<1) return ;
if(AL_StartPos<0) AL_StartPos =0 ;
if(0 > AL_Offset) AL_Offset=0 ;
if(this->size() <= AL_Offset) return ;
if(this->size() < 1 ) return ;
TypeLength VL_Loop =ml_UseLen-AL_SearchLen ;
ZCSearchInfo* VP_CSearchInfo=0 ;
TypeChar* VP_Origin =mpc_Data ;
TypeLength i =AL_StartPos ;
const char* VPC_OriginStart = this->data();
TypeLength VL_OriginLen = this->size();
TypeLength VL_FindPos = -1 ;
TypeLength VL_OffsetNow = AL_Offset ;
while(i<=VL_Loop)
while /*::::::::::::::::::::::::::::::::::::::::::::::*/
(
( VL_FindPos = ZCMainChars::FindPos
( VPC_OriginStart, APC_SearchData,
VL_OriginLen , AL_SearchLen , VL_OffsetNow
)
)
>= 0
)
/*::::::::::::::::::::::::::::::::::::::::::::::::::::*/
{
TypeLength j;
ARR_CPosList.push_back(VL_FindPos);
for(j=0; j<AL_SearchLen; ++j)
{
if(VP_Origin[i+j]!=APC_Search[j]) break;
}/*
///////////////////////////*/
if(j==AL_SearchLen)
{
/* VP_CSearchInfo=&ARR_InfoList.AddTailDefault()->GetData();
위 코드처럼 하면 ARR_InfoList 를 일반화하기가 어렵다. */
VP_CSearchInfo= &(ZCSearchInfo&)ARR_InfoList;
VP_CSearchInfo->mp_Char= VP_Origin+i ;
VP_CSearchInfo->ml_Pos = i ;
VP_CSearchInfo->ml_Len = AL_SearchLen ;
i += AL_SearchLen ;
}
else // j!=AL_SearchLen
{
++i;
}/*
else // j!=AL_SearchLen*/
}/*
while(i<=VL_Loop)*/
VL_OffsetNow = VL_FindPos + AL_SearchLen;
}
/*::::::::::::::::::::::::::::::::::::::::::::::::::::*/
}/*
template<typename TSearchInfoList> void MakeInfoList
template<typename TPosList> void FindPosToList /////////////
(
TypeCharC* APC_Search ,
TypeLength AL_SearchLen,
TypeLength AL_StartPos ,
TSearchInfoList& ARR_InfoList
TPosList& ARR_CPosList, TypeCPChar APC_SearchData,
TypeLength AL_SearchLen, TypeLength AL_Offset=0
)
//////////////////////////////////////////////////*/
##########################################################*/
template<typename TPosList> ZCStringBase& ReplaceToOutByPosList
(
TPosList& AR_CPosList ,
TypeCPChar APC_Replace ,
TypeLength AL_Replace ,
TypeLength AL_Searched ,
ZCStringBase& ARR_SaveOut
)
/*##########################################################*/
{
// TPosList : ZNsMain::ZtCList<TypeLength> etc
// AL_Replace : APC_Replace 의 길이
// AL_Searched : 이전에 찾은 길이
// ARR_SaveOut : AL_Replace>AL_Searched 인 경우에 여기에 저장한다.
if(AR_CPosList.size()<1) return *this;
TypeLength VL_PosListSize= AR_CPosList.size() ;
TypeLength VL_ThisSize = this->size() ;
TypeLength VL_NeedSize = VL_ThisSize +
(AL_Replace-AL_Searched) * VL_PosListSize ;
TypePChar VPC_ThisStart = this->data() ;
IterEasyID VH_IterEasyID = AR_CPosList.ItHID();
TypeLength VL_SearchedPos= 0 ;
TypeLength VL_SearchedPre= 0 ; // VL_SearchedPos 의 이전 값
if(AL_Replace<=AL_Searched) // 메모리 증가 불필요
{
TypePChar VPC_MoveStart = 0 ;
TypePChar VPC_DestStart = 0 ;
TypeLength VL_MoveStart = 0 ;
TypeLength VL_DestStart = 0 ;
TypeLength VL_MemMoveSize= 0 ;
TypePChar VPC_RepalcePos= 0 ;
__for1(TypeLength, i, VL_PosListSize)
{
VL_SearchedPos = AR_CPosList.ItD(VH_IterEasyID) ;
VPC_RepalcePos = VPC_ThisStart + VL_SearchedPos -
( AL_Searched-AL_Replace ) * (i-1) ;
if(VL_MoveStart>VL_DestStart)
{
VL_MemMoveSize =
VL_SearchedPos - VL_SearchedPre - AL_Searched ;
VPC_MoveStart = VPC_ThisStart + VL_MoveStart ;
VPC_DestStart = VPC_ThisStart + VL_DestStart ;
::memmove /*::::::::::::::::::::::::::::::::::::::*/
(
VPC_DestStart, VPC_MoveStart, VL_MemMoveSize
);
/*::::::::::::::::::::::::::::::::::::::::::::::::*/
}/*
if(VL_MoveStart>VL_DestStart)*/
VL_SearchedPre = VL_SearchedPos ;
VL_MoveStart = VL_SearchedPos+ AL_Searched ;
VL_DestStart = VL_SearchedPos+ AL_Searched -
( AL_Searched-AL_Replace ) * i ;
::memcpy(VPC_RepalcePos, APC_Replace, AL_Replace);
AR_CPosList.ItNext(VH_IterEasyID);
}/*
__for1(TypeLength, i, VL_PosListSize)*/
if(VL_DestStart<VL_MoveStart && VL_DestStart<VL_ThisSize)
{
::memmove /*::::::::::::::::::::::::::::::*/
(
VPC_ThisStart + VL_DestStart,
VPC_ThisStart + VL_MoveStart,
VL_MoveStart - VL_DestStart
);
/*::::::::::::::::::::::::::::::::::::::::*/
}/*
if(VL_DestStart<VL_MoveStart && VL_DestStart<VL_ThisSize)*/
this->resize(VL_NeedSize); return *this;
}/*
if(AL_Replace<=AL_Searched) // 메모리 증가 불필요*/
ARR_SaveOut.resize(VL_NeedSize);
TypePChar VPC_OutStart = ARR_SaveOut.data() ;
TypePChar VPC_CopyStart = 0 ;
TypePChar VPC_DestStart = 0 ;
TypeLength VL_CopyStart = 0 ;
TypeLength VL_DestStart = 0 ;
TypeLength VL_MemCopySize= 0 ;
TypePChar VPC_RepalcePos= 0 ;
__for1(TypeLength, i, VL_PosListSize)
{
VL_SearchedPos = AR_CPosList.ItD(VH_IterEasyID) ;
VPC_CopyStart = VPC_ThisStart + VL_SearchedPre ;
VL_DestStart = VL_SearchedPre +
( AL_Replace-AL_Searched ) * (i-1) ;
VPC_DestStart = VPC_OutStart + VL_DestStart ;
if(VL_SearchedPos>VL_SearchedPre)
{
VL_MemCopySize =
VL_SearchedPos - VL_SearchedPre ;
::memcpy /*:::::::::::::::::::::::::::::::::::::::*/
(
VPC_DestStart, VPC_CopyStart, VL_MemCopySize
);
/*::::::::::::::::::::::::::::::::::::::::::::::::*/
}/*
if(VL_SearchedPos>VL_SearchedPre)*/
VL_SearchedPre = VL_SearchedPos + AL_Searched ;
VL_DestStart = VL_SearchedPos +
( AL_Replace-AL_Searched ) * (i-1) ;
VPC_RepalcePos = VPC_OutStart + VL_DestStart ;
::memcpy(VPC_RepalcePos, APC_Replace, AL_Replace) ;
AR_CPosList.ItNext(VH_IterEasyID);
}/*
__for1(TypeLength, i, VL_PosListSize)*/
if(VL_SearchedPre<VL_ThisSize)
{
VL_DestStart = VL_DestStart + AL_Replace ;
VPC_DestStart = VPC_OutStart + VL_DestStart ;
VPC_CopyStart = VPC_ThisStart+ VL_SearchedPre;
VL_MemCopySize = VL_ThisSize - VL_SearchedPre;
::memcpy /*:::::::::::::::::::::::::::::::::::::::*/
(
VPC_DestStart, VPC_CopyStart, VL_MemCopySize
);
/*::::::::::::::::::::::::::::::::::::::::::::::::*/
}/*
if(VL_SearchedPre<VL_ThisSize)*/
return ARR_SaveOut;
}/*
template<typename TPosList> ZCStringBase& ReplaceToOutByPosList
(
TPosList& AR_CPosList ,
TypeCPChar APC_Replace ,
TypeLength AL_Replace ,
TypeLength AL_Searched ,
ZCStringBase& ARR_SaveOut
)
############################################################*/
/* template<typename TSearchInfoList> void MakeSplitInfoList()
APC_Search 문자열로 나뉘어지는 각 구간의 문자열 정보리스트를 얻는다.
*/
template<typename TSearchInfoList> void MakeSplitInfoList
(
TypeCharC* APC_Search ,
@ -383,9 +532,6 @@ namespace ZNsMain
typedef typename
TSearchInfoList::TypeData ZCSearchInfo;
/* void MakeInfoList 함수와는 달리 APC_Search 문자열로
나뉘어지는 각 구간의 문자열 정보리스트를 얻는다. */
if(ml_UseLen<1 || AL_SearchLen<1) return ;
if(AL_StartPos<0) AL_StartPos=0;
@ -1622,158 +1768,37 @@ namespace ZNsMain
ZCStringBase& ReplaceOnce(
TypeCharC* APC_Search, TypeCharC* APC_Replace, TypeLength AL_StartPos=0)*/
ZCStringBase& Replace /*#######################################################*/
ZCStringBase& Replace /*###################################################*/
(
TypeCharC* APC_Search ,
TypeCharC* APC_Replace ,
TypeLength AL_SearchLen ,
TypeLength AL_ReplaceLen ,
TypeLength AL_StartPos=0
TypeCPChar APC_Search, TypeCPChar APC_Replace,
TypeLength AL_Search , TypeLength AL_Replace , TypeLength AL_Offset=0
)
/*#############################################################################*/
/*##########################################################################*/
{
if(ml_UseLen<1) return *this;
if(0 > AL_Offset) AL_Offset=0 ;
if(this->size() <= AL_Offset) return *this;
if(this->size() < 1 ) return *this;
ZCSearchInfoList VO_CSearchInfoList;
MakeInfoList /*<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<*/
(
APC_Search , AL_SearchLen,
AL_StartPos, RR(VO_CSearchInfoList)
);
TypeLength VL_InfoEntrySize = VO_CSearchInfoList.GetSize() ;
if(VL_InfoEntrySize<1) return *this;
TypeLength VL_PrevSize =ml_UseLen;
TypeLength VL_NewSize =0 ;
IterEasyID VI_IterEasyID=
VO_CSearchInfoList.GetHeadIterEasyID();
VL_NewSize = ml_UseLen +
VL_InfoEntrySize*(AL_ReplaceLen-AL_SearchLen );
if(VL_NewSize>VL_PrevSize) ReAllocKeep(VL_NewSize);
TypeChar* VP_Origin=mpc_Data; TypeLength VL_Index=0;
/* AL_ReplaceLen==AL_SearchLen 나
AL_ReplaceLen> AL_SearchLen 나
AL_ReplaceLen< AL_SearchLen 각 경우에
Replace 방식이 조금 틀리다. */
if(AL_ReplaceLen==AL_SearchLen)
{
__for0(TypeLength, i, VL_InfoEntrySize)
{
VL_Index = VO_CSearchInfoList.
ItD(VI_IterEasyID).ml_Pos ;
__for0(TypeLength, j, AL_ReplaceLen)
{ VP_Origin[VL_Index+j] =APC_Replace[j] ; }
VO_CSearchInfoList.MoveNextIter(VI_IterEasyID);
}/*
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>*/
}
else if(AL_ReplaceLen<AL_SearchLen)
{
VL_Index = VO_CSearchInfoList.GetHeadData().ml_Pos;
for(TypeLength i=1; i<=VL_InfoEntrySize; ++i)
{
for(TypeLength j=0; j<AL_ReplaceLen; ++j)
{ VP_Origin[VL_Index++]=APC_Replace[j] ; }
if(i!=VL_InfoEntrySize)
{
// 마지막 링크가 아닐 경우
TypeLength VL_IndexHead =
VO_CSearchInfoList.ItD(VI_IterEasyID ).ml_Pos+AL_SearchLen;
TypeLength VL_IndexTail =
VO_CSearchInfoList.ItD(VI_IterEasyID, 1).ml_Pos-1 ;
for(TypeLength k=VL_IndexHead; k<=VL_IndexTail; ++k)
{ VP_Origin[VL_Index++] = VP_Origin[k] ; }
}
else // i==VL_InfoEntrySize
{
TypeLength VL_IndexTail = VL_PrevSize-1 ;
TypeLength VL_IndexHead =
VO_CSearchInfoList.ItD(VI_IterEasyID).ml_Pos+AL_SearchLen;
for(TypeLength k=VL_IndexHead; k<=VL_IndexTail; ++k)
{
VP_Origin[VL_Index++] = VP_Origin[k] ;
}/*
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>*/
}/*
else // i==VL_InfoEntrySize*/
VO_CSearchInfoList.MoveNextIter(VI_IterEasyID);
}/*
for(TypeLength i=1; i<=VL_InfoEntrySize; ++i)*/
}/*
else if(AL_ReplaceLen<AL_SearchLen)*/
else // AL_ReplaceLen>AL_SearchLen
{
// 뒤부터 채워 나간다.
VP_Origin[VL_NewSize]=0;
VL_Index = VL_NewSize-1 ;
VI_IterEasyID =
VO_CSearchInfoList.GetTailIterEasyID() ;
TypeLength VL_IndexTail = VL_PrevSize-1 ;
TypeLength VL_IndexHead =
VO_CSearchInfoList.ItD(VI_IterEasyID).ml_Pos+AL_SearchLen;
for(TypeLength i=VL_IndexTail; i>=VL_IndexHead; --i)
{
VP_Origin[VL_Index--] = VP_Origin[i];
}/*
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>*/
for(TypeLength j=VL_InfoEntrySize ;j>=2; --j)
{
TypeLength k=0;
for(k=AL_ReplaceLen-1; k>=0; --k)
{ VP_Origin[VL_Index--]=APC_Replace[k]; }
VL_IndexHead=VO_CSearchInfoList.ItD(VI_IterEasyID, -1).ml_Pos+AL_SearchLen ;
VL_IndexTail=VO_CSearchInfoList.ItD(VI_IterEasyID ).ml_Pos-1 ;
for(k=VL_IndexTail; k>=VL_IndexHead; --k)
{ VP_Origin[VL_Index--]=VP_Origin[k] ; }
VO_CSearchInfoList.MovePrevIter(VI_IterEasyID);
}/*
for(TypeLength j=VL_InfoEntrySize; j>=2; --j)*/
for(TypeLength k=AL_ReplaceLen-1; k>=0; --k)
{
VP_Origin[VL_Index--] = APC_Replace[k];
}/*
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>*/
}/*
else // AL_ReplaceLen>AL_SearchLen*/
VP_Origin[ml_UseLen=VL_NewSize]=0; return *this;
}/*
ZCStringBase& Replace ###########################################################
ZtCList<TypeLength> VO_CPosCList; FindPosToList
(
TypeCharC* APC_Search ,
TypeCharC* APC_Replace ,
TypeLength AL_SearchLen ,
TypeLength AL_ReplaceLen ,
TypeLength AL_StartPos=0
RR(VO_CPosCList), APC_Search, AL_Search, AL_Offset
);
/*////////////////////////////////////////////*/
ZCStringBase VO_CStringOut; return *this = ReplaceToOutByPosList
(
VO_CPosCList, APC_Replace, AL_Replace, AL_Search, RR(VO_CStringOut)
);
/*:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::*/
}/*
ZCStringBase& Replace /*######################################################
(
TypeCPChar APC_Search, TypeCPChar APC_Replace,
TypeLength AL_Search , TypeLength AL_Replace , TypeLength AL_Offset=0
)
/*#############################################################################*/
############################################################################*/
ZCStringBase& Replace