Как объявить двумерный массив?


92

Какой самый простой способ создать 2-мерный массив. Я надеялся, что смогу сделать что-то подобное:

declare int d[0..m, 0..n]

Ответы:


81

Вы также можете создать ассоциативный массив или массив, подобный «хеш-таблице», указав индекс массива.

$array = array(
    0 => array(
        'name' => 'John Doe',
        'email' => 'john@example.com'
    ),
    1 => array(
        'name' => 'Jane Doe',
        'email' => 'jane@example.com'
    ),
);

Что эквивалентно

$array = array();

$array[0] = array();
$array[0]['name'] = 'John Doe';
$array[0]['email'] = 'john@example.com';

$array[1] = array();
$array[1]['name'] = 'Jane Doe';
$array[1]['email'] = 'jane@example.com';

1
Как мы можем создать этот же массив, используя операторы цикла?
— Anoop Pete,

@ Anoop-Pete Во втором фрагменте два повторяющихся блока будут помещены в цикл, а числовой индекс заменен переменной, которая увеличивается на каждую итерацию.
— Атли

1
@AnoopPete: for ($ i = 0; $ i <count ($ array); $ i ++) {print ($ array [$ i] ['имя']); }
— Dax

64

Следующие примеры эквивалентны и приводят к двумерному массиву:

$array = array(
    array(0, 1, 2),
    array(3, 4, 5),
);

или

$array = array();

$array[] = array(0, 1, 2);
$array[] = array(3, 4, 5);

7
Это не приводит к двумерным массивам, а скорее к массиву массивов.
— dotancohen

5
@dotancohen На самом деле это просто семантика. Практически эти две концепции совпадают. Единственное различие между тем, что здесь демонстрируется, и типом многомерных массивов, используемых в таких языках, как C #, - это синтаксис. И при этом довольно небольшая разница в синтаксисе.
— Атли

1
По крайней мере, в C # требования к памяти другие. Массив массивов выделяет только объем памяти, необходимый для каждого массива. Двумерный массив занимает все N * M памяти.
— dotancohen 07

6
@dotancohen Требования к памяти между PHP и C # в целом сильно различаются, поскольку среда выполнения каждого языка имеет собственный способ работы с памятью. Обычно это не то, чем вы занимаетесь на практике. Нет, если только вы не создаете какое-то долгое, высокопроизводительное приложение, например игру, и в этом случае PHP будет странным выбором языка.
— Атли

41

Просто заявите? Вы не обязаны. Просто убедитесь, что переменная существует:

$d = array();

Размер массивов изменяется динамически, и попытка записать что-либо в несуществующий элемент создает его (и при необходимости создает весь массив)

$d[1][2] = 3;

Это действительно для любого количества размеров без предварительного объявления.


3
За исключением того, что это ничего не говорит вам о размерах. Если вы объявляете 2D-массив M x N, скорее всего, это матрица, а если это матрица, скорее всего, вы будете выполнять умножение или что-то на нем, что потребует повторения элементов, что вы не можете сделать, если это «редкие» и не знают размеров.
— cletus

@cletus: вы можете просто использовать countправильное измерение, например count($d[1]), если я не понимаю вашу точку зрения?
— DisgruntledGoat

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

27

Во-первых, в PHP нет многомерных массивов, в нем есть массивы массивов.

Во-вторых, вы можете написать функцию, которая будет это делать:

function declare($m, $n, $value = 0) {
  return array_fill(0, $m, array_fill(0, $n, $value));
}

2
Вы имеете в виду «массивы из массивов», вместо «массивов или массивов»?
— Asaph

@ Асаф: да, я сделал. Исправлена. Спасибо.
— cletus

1
Настройка массива нулей - занятие совершенно бессмысленное. Вам не нужно объявлять массив, просто используйте его.
— DisgruntledGoat

8
За исключением случаев, когда вам нужно перебрать его или определить его размер, например, если вы говорите, что делаете матричное умножение. Это вполне допустимый случай для заполнения значений массива.
— cletus

11

Для простого решения типа "заполнять по ходу":

$foo = array(array());

Это даст вам гибкий псевдодвумерный массив, который может содержать $ foo [ n ] [ n ], где n <= ∞ (конечно, вы ограничены обычными ограничениями на размер памяти, но, надеюсь, вы поняли идею). Теоретически это можно расширить, чтобы создать столько подмассивов, сколько вам нужно.


9

Или для больших массивов, все с одинаковым значением:

$m_by_n_array = array_fill(0, $n, array_fill(0, $m, $value);

будет создать с $mпомощью $nмассива со всем набором к $value.


3

Насколько мне известно, для этого нет встроенной функции php, вам нужно сделать это через цикл или через специальный метод, который рекурсивно вызывает что-то вроде array_fill, указанное в ответе @Amber;

Я предполагаю, что вы имеете в виду создание пустого, но инициализированного массива массивов. Например, вам нужны окончательные результаты, подобные приведенному ниже для массива из 3 массивов :

   $final_array = array(array(), array(), array());

Это просто написать код вручную, но для массива произвольного размера, такого как массив из 3 массивов из 3 массивов, он начинает усложнять инициализацию перед использованием:

     $final_array = array(array(array(), array(), array()), array(array(), array(), array()), array(array(), array(), array()));

...так далее...

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


3

Ответ Атли действительно помог мне понять это. Вот пример того, как перебирать двумерный массив. В этом примере показано, как найти значения для известных имен массива, а также foreach, в котором вы просто просматриваете все поля, которые там находите. Надеюсь, это кому-то поможет.

$array = array(
    0 => array(
        'name' => 'John Doe',
        'email' => 'john@example.com'
    ),
    1 => array(
        'name' => 'Jane Doe',
        'email' => 'jane@example.com'
    ),
);

foreach ( $array  as $groupid => $fields) {
    echo "hi element ". $groupid . "\n";
    echo ". name is ". $fields['name'] . "\n";
    echo ". email is ". $fields['email'] . "\n";
    $i = 0;
    foreach ($fields as $field) {
         echo ". field $i is ".$field . "\n";
        $i++;
    }
}

Выходы:

hi element 0
. name is John Doe
. email is john@example.com
. field 0 is John Doe
. field 1 is john@example.com
hi element 1
. name is Jane Doe
. email is jane@example.com
. field 0 is Jane Doe
. field 1 is jane@example.com

2

И для меня аргумент о том, должен ли массив быть разреженным или нет, зависит от контекста.

Например, если $ a [6] [9] не заполнено, это эквивалентно заполнению $ a [6] [9], например, "" или 0.


2
$r = array("arr1","arr2");

чтобы отобразить один элемент массива, вы должны написать:

echo $r[0];
echo $r[1];

вывод будет: arr1 arr2


2
Это одномерный массив. В многомерном массиве есть как минимум массив внутри массива.
— Майк Стрэттон

2

А мне так нравится:

$cars = array
  (
  array("Volvo",22),
  array("BMW",15),
  array("Saab",5),
  array("Land Rover",17)
  );

0

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

$array = Arr::setNestedElement([], '1.2.3', 'value');

который будет производить

[
  1 => [
    2 => [
      3 => 'value'
    ]
  ]
]

0

Вы можете попробовать это, но значения второго измерения будут равны индексам:

$array = array_fill_keys(range(0,5), range(0,5));

немного сложнее для пустого массива:

$array = array_fill_keys(range(0, 5), array_fill_keys(range(0, 5), null));


0

Вам нужно объявить массив в другом массиве.

$arr = array(array(content), array(content));

Пример:

$arr = array(array(1,2,3), array(4,5,6));

Чтобы получить первый элемент из массива, вы будете использовать его $arr[0][0], как первый элемент из первого массива из массива. $arr[1][0]вернет первый элемент из второго массива из массива.

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.