阵列中的模式出现

时间:2015-11-07 00:22:36

标签: c arrays pointers

我的任务是编写一个程序来计算字符序列在另一个字符序列中出现的次数。 '模式'函数应该返回第一个序列在第二个序列中出现的次数而不重复。由于这是一个编程练习,我不允许使用括号来取消引用指针,并且只能使用指针算法。

我决定使用if语句来查看数组中是否出现了序列。我很难看到问题所在。我打印出pValue1以查看指针在数组中的位置。任何帮助将不胜感激。

#include <stdio.h>
#include <string.h>

int pattern(char *ptr1, char *ptr2)
{
char *pValue1 = ptr1;
char *pValue2 = ptr2;
int count = 0;
int occurrence = 0;

while (*pValue1 != '\0')
{
    if (*pValue1 == *pValue2)
    {
        if (*pValue1++ == *pValue2++)
        {
            if (*pValue1 + 2 == *pValue2 + 2)
            {
                printf("Occurence happens at Location: %d", count);
                occurrence++;

            }
        }
    }
    count++;
    pValue1 = pValue1 + count;
    printf("%d", pValue1);
}
/* Print number of occurrences. */
printf("number of occurrences: %i \n", occurrence);


}


void main()
{
char array1[] = "1','1','0','1','0','0','1','1','1','0','1','1','\0'";
char array2[] = "'1','0', '1', '\0'";


pattern(array1, array2);
getchar();
getchar();
}

2 个答案:

答案 0 :(得分:2)

您的比较代码相当混乱。这条线可能没有按照您的预期行事:

if (*pValue1 + 2 == *pValue2 + 2)

取消引用每个指针,然后将2加到结果中。我觉得你 打算这样:

if (*(pValue1 + 2) == *(pValue2 + 2))

以此为目的,代码仍然是错误的。首先,你比较 [0]处的字符:

if (*pValue1 == *pValue2)

然后递增指针,并比较[1]处的字符:

if (*pValue1++ == *pValue2++)

然后检查[3]处的字符:

if (*(pValue1 + 2) == *(pValue2 + 2))

所以,你正在跳过[2],而你只是检查几个字符。您 需要一个循环来检查第一个字符串中的所有内容 你正在检查第二个字符串。

此外,您似乎正在调用pattern()来检查整秒 串?但是那时你只是检查它的开头。你需要一个 外循环迭代第二个字符串的每个部分。

main()中的第一行通常会以这种方式编写:

char array1[] = "110100111011";
char array2[] = "101";

我还建议将参数重命名为needlehaystack 使代码更具可读性。

答案 1 :(得分:2)

使用指针算法通常很痛苦,因为使用指针通常是危险的,需要额外注意以避免问题。我建议你找到一个可能的解决方案,制作更小的步骤,并确保你理解每一个。

让我们从你的程序的骨架开始:

#include <stdio.h>

/* declaration of functions */

int main(void) {

/* declaration of global variables */
/* main stuff */

return 0;
}

您正在使用空终止字符数组,您可以通过多种方式声明和初始化它们(但不是您如何做到这一点......):

/* declaration of global variables */

char source[] = "110100111011";             
char pattern[] = { '1', '0', '1', '\0' };

为了解决你的任务,我会实现一个简单(但效率低下)的算法,但在跳转到实际函数之前,我会尝试编写一些易于测试你(以及我的)对指针的理解的东西。例如,编写一个函数,该函数计算那些数组中为空终止符所执行的字符数。 如果你不能,请看看这个:

int charArrayLength ( char * str ) {
    char * pch;

    if (str) {
        pch = str;
        while ( *pch ) pch++;
        return pch - str;
    }
    else return 0;
}

注意它在使用之前如何检查作为参数传递的指针以及如何使用某些指针算法计算长度。这很难看,但似乎有效。 如果它全部清楚(并经过测试!总是确保一个函数完成它的工作)让我们继续前进并编写一个函数来搜索数组中的字符并将其第一次出现的位置作为整数返回(如果不是则返回-1) :

int posCharInString ( char * c, char * str) {
    char * p;

    if (str && c) {
        p = str;
        while ( *p ) {
            if ( *p == *c ) return p - str;
            p++;
        }
    }
    return -1;
}

再次,测试它并尝试理解它是如何工作的(或者它为什么不工作......)。现在我们离得更近了。让我们转换这个函数,以便它可以搜索数组中的一系列字符,并将它的第一次出现的位置作为整数返回(如果不是则返回-1):

int posStringInString ( char * pat, char * str) {
char * p;
char * s;
char * k;

if (str && pat) {
    p = str;
    while ( *p ) {
        s = pat;
        k = p;
        do {
            if ( *s == *k ) {
                s++;
                k++;
            } else break;
        } while ( *s && *k);
        if ( *s ) p++;
        else return p - str;
    }
}
return -1;
}

我添加了一个嵌套循环来检查corrispondence。现在我们只需要查找所有出现的内容,并且我将使用另一个调用最后一个函数的函数:

int occurrenceOfStringInString ( char * pat, char * str) {
    int sum = 0;
    int pos = 0;
    int posrel = posStringInString(pat,str);

    while (posrel != -1 ) {
        pos += posrel;
        sum++;
        printf("Occurrence: %i, position: %i\n",sum,pos);
        ++pos;
        posrel = posStringInString(pat,str + pos);
   }
   return sum;  
}

注意++ pos从下一个位置开始搜索。就是这样,只需重写我们的主要内容:

int main(void) {
    char sequence[] = "110100111011";
    char pattern[] = "101";

    printf("Total occurrences: %i\n",occurrenceOfStringInString(pattern,sequence));

    getchar();

    return 0;
}