一问题: 给定一组字符串,要求求出一个最短的字符串使得它包含所有给出的字符串。
比如"a","bc","ca".输出应该是"bca"。
算法: 1、设置结构数组len,记录每个字符串的长度和下一个字符串的 将字符串集合中的最长的字符串作为要求的最短字符串string
2、按照数组len的记录长度,在剩下的字符串中找出记录长度最长的 字符串,
a. 如果这个字符串包含在string中,该字符串已被包含,转2;
b. 如果这个字符串的长度是1,将该字符串与string连接, 该字符串已被包含,转2;
c. 如果这个字符串的长度与它在数组len的记录长度相等, 将它在数组len的记录长度减1,转2;
d. 如果这个字符串的长度与它在数组len的记录长度length不相等, 分别取该字符串的左右length个字符子串,如果子串包含在 string中,将剩下的字符连接到string中, 该字符串被包含,转2;否则将它在数组len的记录长度减1,转2。
#define StringNum 100
#define MaxLength 100
struct node
{
unsigned length;
unsigned index;
};
int IsInString(char *str,char *s);
int MaxLen(struct node len[],int s,int n);
void Swap(struct node *t1,struct node *t2);
void LeftStr(char *s,char *d,int n);
void RightStr(char *s,char *d,int n);
int SimplyKMP(const char* src, const char* token);
int FindMaxLen(char* str[], int num, BOOL bFind[]);
void FindMinStr(char* str[], int num, char* res);
void main(void)
{
char *str[StringNum];
char string[MaxLength],s[MaxLength],s1[MaxLength],*s0;
int i,num,max;
struct node len[StringNum];
printf("/nPlease input the number of strings: ");
scanf("%d",&num);
getchar();
printf("/nPlaese input each string: /n");
for(i=0;i<num;i++)
{
gets(s);
len[i].length=strlen(s);
len[i].index=i;
str[i]=(char *)malloc(sizeof(char)*(len[i].length+1));
strcpy(str[i],s);
}
i=0;
max=MaxLen(len,i,num);
Swap(&len[i],&len[max]);
strcpy(string,str[len[i].index]);
len[i].index=-1;
i++;
while(i<num)
{
max=MaxLen(len,i,num);
Swap(&len[i],&len[max]);
s0=str[len[i].index];
if( IsInString(string,s0) )
{
len[i].index=-1;
i++;
continue;
}
if (len[i].length==0)
{
strcat(string,s0);
len[i].index=-1;
i++;
continue;
}
if (strlen(s0)==1)
{
strcat(string,s0);
len[i].index=-1;
i++;
continue;
}
if (len[i].length!=strlen(s0))
{
LeftStr(s0,s,len[i].length);
RightStr(string,s1,len[i].length);
if (!strcmp(s,s1))
{
RightStr(s0,s,strlen(s0)-len[i].length);
strcat(string,s);
len[i].index=-1;
i++;
continue;
}
else
{
RightStr(s0,s,len[i].length);
LeftStr(string,s1,len[i].length);
if (!strcmp(s,s1))
{
LeftStr(s0,s,strlen(s0)-len[i].length);
strcat(s,string);
strcpy(string,s);
len[i].index=-1;
i++;
continue;
}
}
}
len[i].length--;
}
printf("/nThe result string is: ");
puts(string);
int tres = SimplyKMP("bababcaaabb","bcab");
}
/* 寻找字符串数组中长度最大的字符串的位置 */
int MaxLen(struct node len[],int s,int n)
{
int i,max=s;
for(i=s+1;i<n;i++)
if(len[i].length>len[max].length) max=i;
return max;
}
/* 交换数组元素 */
void Swap(struct node *t1,struct node *t2)
{
struct node t;
t=*t1;
*t1=*t2;
*t2=t;
}
/* 取字符串s的左边n个字符串存放到d中 */
void LeftStr(char *s,char *d,int n)
{
strcpy(d,s);
if (n>=strlen(s) || n==0) return;
d[n]=0;
return;
}
/* 取字符串s的右边n个字符串存放到d中 */
void RightStr(char *s,char *d,int n)
{
strcpy(d,s);
if (n>=strlen(s) || n==0) return;
strcpy(d,s+strlen(s)-n);
return;
}
/* 如果字符串s是字符串str的子串,返回1;否则,返回0 */
int IsInString(char *str,char *s)
{
int i,j,p,length,len;
length=strlen(str);
len=strlen(s);
for(i=0;i<=length-len;)
{
p=i+1;
for(j=0;j<len;j++)
{
if (str[i]==s[j]) i++;
else break;
}
if (j==len) return 1;
i=p;
}
return 0;
}
void FindMinStr(char* str[], int num, char* res)
{
char temp[MAX_PATH] = {0};
BOOL* bFlag = new BOOL[num];
for (int index = 0; index < num; index++)
bFlag[index] = FALSE;
int maxLen = FindMaxLen(str, num, bFlag);
bFlag[maxLen] = TRUE;
strcpy(temp, str[maxLen]);
index = 0;
while(index < num)
{
maxLen = FindMaxLen(str, num, bFlag);
if (SimplyKMP(str[maxLen], temp) > 0)
{
bFlag[maxLen] = TRUE;
index++;
continue;
}
if (strlen(str[maxLen]) == 1)
{
strcat(temp, str[maxLen]);
bFlag[maxLen] = TRUE;
index++;
continue;
}
}
}
int FindMaxLen(char* str[], int num, BOOL bFind[])
{
int maxLen = 0;
for (int i = 0; i < num; ++i)
{
if (bFind[i])
break;
int len = strlen(str[i]);
if (maxLen < len)
maxLen = len;
}
return maxLen;
}
int SimplyKMP(const char* src, const char* token)
{
int i = 0;
int j = 0;
while(i < strlen(src) && j < strlen(token))
{
if (src[i] == token[j])
{
i++;
j++;
}
else
{
i = i - j + 1;
j = 0;
}
}
if (j >= strlen(token))
return i - strlen(token);
return -1;
}
二求数组中最长的单调递增子序列
void ShowRes(int* a, int* pMax, int MaxD, int k)
{
if (k == -1)
return;
if (pMax[k] == MaxD)
{
ShowRes(a, pMax, MaxD - 1, k - 1);
printf("%d", a[k]);
}
else
{
ShowRes(a, pMax, MaxD, k - 1);
}
}
void FindMaxIncSquence(int* a, int n)
{
int max[n], nMax = 1, k = 1;
for (int i = 0; i < n; i++)
max[i] = 0;
for (int i = 1; i < n; i++)
{
for (int j - 0; j < n; j ++)
{
if (a[i] > a[j] && max[i] <= max[j])
max[i] = max[j] + 1;
}
if (nMax < max[i])
{
nMax = max[i];
k = i;
}
}
ShowRes(a, max, nMax, k);
}
Node* Reverse(Node* pHeade)
{
Node* p = pHeade->pNext;
Node q = NULL;
if (p != NULL)
{
q = p->pNext;
p->pNext = NULL;
while (q != NULL)
{
p = q;
q = q->pNext;
p->pNext = pHeade->pNext;
pHeade->pNext = p;
}
}
return pHeade;
}
struct BTree
{
char Data;
BTree* pLeft;
BTree* pRight;
};
BTree* CreaateTree(char* pPre, char* pInner, int nLen)
{
char* pTemp = *pInner;
int k = 0;
while(*pTemp++ != *pPre)
k++;
BTree* pNode = new BTree;
pNode->Data = * pPre;
pNode->pLeft = CreaateTree(pPre + 1; pInner, k);
pNode->pRight = CreaateTree(pPre + 1 + k, pInner, n - 1 - k);
return pNode;
}