【问题标题】:Searching for matching elements between 2 arrays in C在C中搜索2个数组之间的匹配元素
【发布时间】:2021-08-19 04:01:02
【问题描述】:

问题

有两个数组,一个包含大量数字 (arr1),可能有一些重复序列,例如 1,2,4 可能在此数组中重复多次。用户将分配另一个数组 (arr2)。

我需要一种方法来搜索arr1 以获取用户为arr2 提供的确切输入。为了使匹配有效,所有元素的顺序必须与用户输入的顺序完全相同。

例如,如果用户输入 1,2,4,3,则程序必须在 arr1 中按确切顺序找到 1,2,4,3,这意味着 arr1 中的 1,2,3,4不应该算作匹配。以下是我到目前为止所能想到的,但即使只有 2 个数组的第一个元素匹配,它也会返回 true。

for (int i=0; i<size1; i++)

{

for (int j = 0; j<size2; j++)

{

if(arr1[i] == arr2[j])

{

printf("found a match %d", j);

break;

}

else if (arr1[i] != arr2[j])

{

printf("not match");

break;

}

下面是完整的代码:-

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

int main()
{
    int arr1[] = {1, 2, 4, 2, 2, 2, 1, 1, 2, 4, 3, 4, 4, 1, 2, 4, 4, 1, 3, 3};
    int size1 = (int) (sizeof(arr1)/sizeof(arr1));
    
    int arr2[] = {1, 2, 4};
 
 
 
    int size2 = (int) (sizeof(arr2)/sizeof(arr2[0]));

       int match = 0;        
        for (int i=0; i<size1; i++)      
        {
    
            for (int j = 0; j < size2; j++) {
    
                if (arr1[i] != arr2[j]) {
                    match = 1;
                    break;
    
                }
            }
        }
        if(match == 1){
            printf("Not a match");
        }else if(match == 0){
            printf("The lists match");
        }
        return 0;
}

如果您查看arr1arr2,我需要一种方法来返回索引0、7、13,而且这仍然很粗糙,因为arr2 在技术上是动态的,因为它是由用户分配的,并且没有固定大小,只有arr1 会有固定大小。

【问题讨论】:

    标签: arrays c for-loop search


    【解决方案1】:

    您的问题类似于在字符串中查找子字符串。但是字符被替换为整数。

    这是一个查找匹配项的程序。它有一些调试打印语句来显示它是如何工作的。

    #include <stdio.h>
    int g_Arr2_Changed=0; //----Global boolean if arr2 changes.
    int main(int argc, const char *argv[])
    { int arr1[] = {1, 2, 4, 2, 2, 2, 1, 1, 2, 4, 3, 4, 4, 1, 2, 4, 4, 1, 3, 3};
      int size1 = (int) (sizeof(arr1)/sizeof(int));
      int arr2[] = {1, 2, 4};
      int size2 = (int) (sizeof(arr2)/sizeof(int));
      int patternStart  = -1; //----Start pattern in arr1.
      int nPatternMatch =  0; //----Number of ints matched so far.
      for (int i=0; i<size1; i++)
      { int checkInt = arr1[i];
        //printf("[%i](%i)", i, checkInt);
        if (nPatternMatch == 0) //----No integers are matched yet.
        { //printf("<None>");
          //----Is checkInt the start of arr2?
          if (arr2[nPatternMatch] == checkInt)
          { patternStart=i; nPatternMatch++; //printf("<start>");
          }
        }
        else //----At least one integer has been matched already.
        { //printf("<Some>");
          //----Is checkInt a continuation?
          if (arr2[nPatternMatch] == checkInt)
          { nPatternMatch++; //----Matched another integer.
            //printf("<matched>");
          }
          else
          { //printf("<NotMatched>");
            i = patternStart; //---- for() will add one.
            patternStart = - 1;
            nPatternMatch = 0; //----Not match. Start at next int.
          }
        }
        //----If match found print and reset for next.
        if (nPatternMatch == size2)
        { printf("Pattern found at %i\n", patternStart);
          i = patternStart + 1;
          patternStart = -1; nPatternMatch = 0;
        }
        //----Just in case the global variable says arr2 changed.
        if (g_Arr2_Changed != 0) //----Start over.
        { //printf("<arr2 changed.>");
          i=0; patternStart = -1; nPatternMatch = 0;
          size2 = (int) (sizeof(arr2)/sizeof(int));
        }
        //printf("\n");
      }
      return 0;
    }
    

    【讨论】:

      【解决方案2】:

      请您尝试以下方法:

      #include <stdio.h>
      
      int main()
      {
          int arr1[] = {1, 2, 4, 2, 2, 2, 1, 1, 2, 4, 3, 4, 4, 1, 2, 4, 4, 1, 3, 3};
          int size1 = sizeof arr1 / sizeof arr1[0];
      
          int arr2[] = {1, 2, 4};
          int size2 = sizeof arr2 / sizeof arr2[0];
      
          int match;
          int i, j;
      
          for (i = 0; i < size1 - size2 + 1; i++) {
              match = 0;
              for (j = 0; j < size2; j++) {
                  if (arr1[i + j] != arr2[j]) {
                      match = 1;
                      break;
                  }
              }
              if (! match) {
                  printf("matched at %d\n", i);
              }
          }
          return 0;
      }
      

      它会输出:

      matched at 0
      matched at 7
      matched at 13
      

      如果你想将一个数组分配给匹配的索引列表,你可以很容易地修改代码。

      【讨论】:

        【解决方案3】:

        此代码将为两个列表中相同位置的每个字符返回一个匹配项。
        因此,如果您想验证整个列表,您应该设置一个 int,以识别是否有一个字符在两个列表中都不匹配。
        如果要显示匹配的列表,只需在第二个 if 中打印整个列表。

                int match = 0;        
                for (int i=0; i<size1; i++)      
                {
            
                    for (int j = 0; j < size2; j++) {
            
                        if (arr1[i] != arr2[j]) {
                            match = 1;
                            break;
            
                        }
                    }
                    if(match == 1){
                        printf("Not a match");
                    }else if(match == 0){
                        printf("The lists match");
                        printf("First character: %c", arr2[0]);
                    }
                    match = 0; 
                }
                
        

        【讨论】:

        • 你可以问我任何问题
        • 嘿,谢谢你的帮助,但我仍然有一些问题,基本上我的问题是 arr1 将是一个固定数组,但 arr2 将是动态的,因为用户将分配所以我需要一个方法比较用户提供给 arr1 的任何元素,并且仅在整个用户字符串与 arr1 匹配时才返回一些内容。如果您可以查看,我在原始问题中提供了更多代码。在 arr1 中, arr2 的字符串重复了多次,所以我需要我的程序找到它重复的所有次数,并返回字符串中第一个数字的索引。 output: 0, 7, 13 应该是输出。
        • 我修改了代码,分别显示 arr2 的任何字符串是否匹配,并显示该字符串的第一个字符。
        • 我再次尝试了代码,由于某种原因,它打印出 Not a Match,但 arr2 被分配为 int arr2[] = {1, 2, 4};在 arr1 中出现 3 次。另外,我不明白您的程序将如何验证 1,2,4 是否都按顺序出现在 arr1 中,因为如果它是 1,4,4,则不应将其视为匹配列表。最后,我不需要一种方法来返回数组的第一个字符,而是我需要一种方法来返回找到所有匹配项的索引,所以如果我们使用 arr2 is 1,2,4 它应该告诉我们找到它的索引是 0,7,13
        猜你喜欢
        • 1970-01-01
        • 2011-01-08
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-05-25
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多