Каково правильное определение указателя на постоянный массив?

0

Я хочу реализовать функцию, которая должна вернуть указатель на массив в C++, что-то вроде:

typedef double* ptr;
ptr func(size_t m) {
  return A[m];
}

где A - двумерный массив, определенный глобально (или как член реализующего класса).

Теперь я хочу убедиться, что возвращаемый массив не может быть изменен вызывающим. Мне было интересно, как я могу объявить возвращаемый тип функции, чтобы гарантировать это.

Я попытался определить его как:

const ptr func(size_t m) {
  return A[m];
}

но я могу написать:

ptr x = func(5); 
x[10] = 20.4;

и выше компилируется без каких-либо проблем.

Теги:
arrays
pointers
function

2 ответа

3

Учитывая следующий код:

#include <stdlib.h>

static double A[100][100];

const double* func(size_t m) {
      return A[m];
}

int main() {
    double * x = func(5);
    x[10] = 20.4;
}

Отчеты GCC 4.8.1:

foo.cc:10:21: error: invalid conversion from ‘const double* to ‘double* [-fpermissive]
  double * x = func(5);
                     ^

Отчеты Clang 3.3:

foo.cc:10:11: error: cannot initialize a variable of type 'double *' with an rvalue of type 'const double *'
        double * x = func(5);
                 ^   ~~~~~~~

И для комментирования комментария ComicSansMS, потому что комментарий, на который он отвечает, был удален:

typedef double* ptr;

const ptr func(size_t m) {
    return A[m];
}

Этот код не совпадает с кодом, указанным выше. const ptr - постоянный указатель на double. Исходный код относится к указателю на константу double.


Вы могли бы что-то сделать в этом направлении:

typedef double* ptr;
typedef const double* cptr;

cptr func(size_t m) {
    return A[m];
}

int main() {
    ptr x = func(5);
    x[10] = 20.4;
}

Что сообщит об ошибке:

so.cc:27:6: error: cannot initialize a variable of type 'ptr' (aka 'double *') with an rvalue of type 'cptr' (aka 'const double *')
        ptr x = func(5);
            ^   ~~~~~~~
  • 0
    VC ++ 2008 выдает ошибку C2440 : 'initializing' : cannot convert from 'const double *' to 'double *'
  • 0
    VC ++ 2012: ошибка C2440: «инициализация»: невозможно преобразовать из «const double *» в «double *». Преобразование теряет квалификаторы.
Показать ещё 8 комментариев
2

const double* и double const* указывают указатель на константу double. Пользователь может изменять, на что ссылается указатель, но не на указанное значение.

double * const указывает постоянный указатель на double. Пользователь может изменить значение указателя в double, но не там, где указатель указывает.

double const * const указывает постоянный указатель на константу double. Пользователь не может изменять либо значение двойника, либо ссылку на указатель.

Ещё вопросы

Сообщество Overcoder
Наверх
Меню