Nano Hash - криптовалюты, майнинг, программирование

Ошибка при передаче 2d-массива в качестве аргумента функции в C++

Я пытаюсь передать 2d-массив функции, но компилятор показывает ошибку:

ошибка: невозможно преобразовать int (*)[5] в int** для аргумента 1 в int max_size(int**, int, int)

Я знаю теорию, но не могу понять, почему она не работает.

    #include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>

#define r 6
#define c 5

using namespace std;

int max_size(int *g[],int m,int n)
{
    // Initial Structure for DP
    int i,j;
    int **s = (int **) malloc (r*sizeof(int *));
    for(i=0;i<r;i++)
        s[i]=(int *)malloc(c*sizeof(int));
    memset(s,0,sizeof(s));

    // Initialization for DP
    for(i=0;i<r;i++)
        s[i][0] = g[i][0];
    for(i=0;i<c;i++)
        s[0][i] = g[0][i];

    // Formulation for DP

    for(i=1;i<r;i++)
    {
        for(j=1;j<c;j++)
        {
            if(g[i][j])

                s[i][j]= min(s[i-1][j],s[i-1][j-1],s[i][j-1])+1;

            else
                s[i][j]=0;
        }
    }

    int c = 0;

    for(i=0;i<r;i++)
    {
        for(j=0;j<c;j++)
        {
            if(s[i][j]>c) c=s[i][j];
        }
    }

return c;
}


int main()
{
   int m[r][c] = {{1,0,1,1,1},{1,1,1,0,0},{1,0,0,0,1},{1,1,0,0,0},{1,0,0,0,1}};
   cout<<max_size(m,r,c);
   return 0;
}
01.01.2015

  • @ Jarod42 справедливое замечание. 01.01.2015
  • Вы задали один и тот же вопрос дважды? Зачем? это ответ, который я вам дал, я думаю, что это хороший ответ. 01.01.2015
  • @iharob Еще одна помощь, ожидаемый неквалифицированный идентификатор перед числовой константой в строке int c =0; Почему возникает ошибка, я пытался найти, но не смог ее исправить. 01.01.2015
  • поскольку c является макросом, вы не можете объявить переменную с таким именем и не можете присвоить c, поскольку макросы заменяются препроцессором во время компиляции, ошибочная строка заменяется на int 5 = 0;, поэтому вы понимаете, почему возникает ошибка. 01.01.2015
  • @iharob большое спасибо. 01.01.2015

Ответы:


1

Вы пытаетесь передать 2D-массив в качестве аргумента типа int**. Такое преобразование невозможно, потому что они будут иметь принципиально разные структуры.

Двумерный массив (например, 3x3) выглядит в памяти так:

  0,0   0,1   0,2   1,0   1,1   1,2   2,0   2,1   2,2
┌─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┐
│ int │ int │ int │ int │ int │ int │ int │ int │ int │
└─────┴─────┴─────┴─────┴─────┴─────┴─────┴─────┴─────┘

int** при использовании в качестве своего рода двумерного массива (где самый внешний указатель указывает на первый элемент в массиве указателей, и каждый из этих указателей указывает на первый элемент в массиве целых чисел) выглядит следующим образом:

┌─────┐
│     │ // The int**
└──╂──┘
   ┃
   ▼
┌─────┬─────┬┄
│     │     │   // An array of int*
└──╂──┴──╂──┴┄
   ┃     ┗━━━━━━━━━━┓
   ▼                ▼
┌─────┬─────┬┄   ┌─────┬─────┬┄
│ int │ int │    │ int │ int │    // Arrays of ints
└─────┴─────┴┄   └─────┴─────┴┄
  0,0   0,1        1,0   1,1

Однако 2D-массив типа int[x][y] можно преобразовать в тип int(*)[y] (в общем случае это называется преобразованием массива в указатель), поэтому вы можете написать свою функцию следующим образом:

int max_size(int (*g)[c],int m,int n);

В качестве альтернативы это можно записать с помощью некоторого синтаксического сахара, например:

int max_size(int g[][c],int m,int n);

Параметры типа массива (вроде этого) преобразуются в указатели, то есть [] вообще не говорит "массив". На самом деле, вы можете указать размер в этих скобках, но он будет полностью проигнорирован.

01.01.2015

2

Я совершенно уверен, что вы должны объявить размер своего массива в объявлениях и инициализациях функций.

int max_size(int *g[] должно быть int max_size(int *g[5] или любым другим размером массива.

01.01.2015
  • Я не уверен в этом, что не так с передачей указателя на указатель. 01.01.2015
  • @edbale Это не указатели, а объявления массивов. Есть разница! 01.01.2015
  • int *g[] точно такой же, как int *g[5] в C++ 01.01.2015
  • И они оба такие же, как int** g (пояснение: как типы параметров функции), в чем проблема. 01.01.2015

  • 3

    Сдача

    int max_size(int *g[],int m,int n)
    

    To

    int max_size(int g[][c],int m,int n)
    
    01.01.2015
  • Вы опускаете неправильный размер. Вы можете опустить только первое измерение. 01.01.2015
  • Ага. Спасибо что подметил это. 01.01.2015

  • 4

    int a[6][5]; определяет единый массив памяти, поддерживающий синтаксис длины шага.

    int * a[] и int ** a не предоставляют длину шага (или размер строки или столбца в зависимости от того, как вы хотите об этом думать) и определяют массив указателей на другую память, а не на один блок памяти, как это делает int a[6][5];.

    01.01.2015

    5

    Есть определенные способы сделать это

    1) Когда второе измерение доступно глобально (в виде макроса или глобальной константы).

    int max_size(int g[][c],int m,int n)
    

    2) Использование одного указателя

    void max_size(int *g, int m, int n) and call it as
    max_size((int *)m,r,c)
    

    3) Использование массива указателей или двойного указателя

    void max_size(int *g[], int m, int n) and call it as
    
    max_size((int **)m,r,c)
    

    Любой из них будет работать. Просто, как вы хотите использовать.

    01.01.2015
    Новые материалы

    Кластеризация: более глубокий взгляд
    Кластеризация — это метод обучения без учителя, в котором мы пытаемся найти группы в наборе данных на основе некоторых известных или неизвестных свойств, которые могут существовать. Независимо от..

    Как написать эффективное резюме
    Предложения по дизайну и макету, чтобы представить себя профессионально Вам не позвонили на собеседование после того, как вы несколько раз подали заявку на работу своей мечты? У вас может..

    Частный метод Python: улучшение инкапсуляции и безопасности
    Введение Python — универсальный и мощный язык программирования, известный своей простотой и удобством использования. Одной из ключевых особенностей, отличающих Python от других языков, является..

    Как я автоматизирую тестирование с помощью Jest
    Шутка для победы, когда дело касается автоматизации тестирования Одной очень важной частью разработки программного обеспечения является автоматизация тестирования, поскольку она создает..

    Работа с векторными символическими архитектурами, часть 4 (искусственный интеллект)
    Hyperseed: неконтролируемое обучение с векторными символическими архитектурами (arXiv) Автор: Евгений Осипов , Сачин Кахавала , Диланта Хапутантри , Тимал Кемпития , Дасвин Де Сильва ,..

    Понимание расстояния Вассерштейна: мощная метрика в машинном обучении
    В обширной области машинного обучения часто возникает необходимость сравнивать и измерять различия между распределениями вероятностей. Традиционные метрики расстояния, такие как евклидово..

    Обеспечение масштабируемости LLM: облачный анализ с помощью AWS Fargate и Copilot
    В динамичной области искусственного интеллекта все большее распространение получают модели больших языков (LLM). Они жизненно важны для различных приложений, таких как интеллектуальные..