const char[N], где N - это число символов строки включая терминальный символ.// Это будет изменяемый двумерный массив указателей на строковые литералы.
const char* dictionary [][2] = {
{ "sads", "asda" },
{ "", "" },
};const в том, что модификатор говорит о неизменяемости определяемого значения.
Но Я читал что и в массиве символов Я тоже могу не ставить const,
а вот если Я создаю именно указатель на символьную строку, то const необходим.
const char* foo = "bar"; - тут "bar" является строковым литералом без размещения. В момент обращения к адресу строкового литерала компилятор для литерала создает размещение со статической продолжительностью хранения. Адрес этого размещения и передается для инициализации foo. Тип размещения определяется как const char[4], тип foo может быть только const char* (изменяемый указатель на неизменяемый символ) или const char* const (неизменяемый указатель на неизменяемый символ).char foo[] = "bar"; - тут в отношении "bar" ничего не меняется, но меняется методика инициализации foo. В таком случае размещение литерала уже не требуется (но возможно в ряде случаев), но требуется размещение переменной foo, которое должно быть инициализировано значением литерала. При этом, сама foo будет полноценно изменяемой и после размещения поучит тип char[4].const и получить массив изменяемых символов, которые были инициализированы литералом.char *dictionary [][2] = ... - тут у тебя двумерный массив указателей на символ. Если ты инициализируешь свой двумерный массив строковыми литералами (а ты именно это и делаешь), компилятор потребует от тебя указать const char* dictionary [][2], т.к. только такая форма в твоем случае будет синтаксически верной.const char* dictionary [][2] означает что ты можешь менять сами указатели в своем двумерном массиве. Если тебе надо чтобы указатели менять было нельзя, тип определения должен быть таким: const char* const dictionary [][2].