通过PHP中的整数索引访问关联数组


92

我想使用键/值对的数组索引来设置关联数组的值。例如:

$my_arr = array( "bling" => "some bling", "bling2" => "lots O bling" );
$my_arr[1] = "not so much bling";  // Would change the value with key bling2.

不使用密钥字符串怎么能做到这一点?

Answers:


188

使用array_keys

$keys = array_keys($my_arr);
$my_arr[$keys[1]] = "not so much bling";

希望这可以帮助。


4
附带说明一下,PHP开发人员为什么会创建这种非直观的数组访问方式?
Marty

3
@Marty与PHP开发人员如何实现它无关,而与您对数组如何工作的误解有关。从技术上讲,以上仍使用关联名称。数字和关联索引键之间没有关联。
Gordon

2
您创建一个关联数组,因为要查找的内容比其在数组中的位置更重要。我认为这是一个好点。假设您有一个数组,其中学生姓名为键,地址为值。您可以通过学生的名字到达学生的地址。数组的位置无关紧要。您可以按排序数组name of the student
多诺万

@Gordon从技术上讲是真的。但是程序员提供的是数字,而不是字符串。我认为这是的意思without using a key string
多诺万

2
@Albert,您正在将此数字映射到适当的密钥字符串。但这并不意味着array[1] === $array['foo']。该数组仍可以包含另一个值$array[1]。请注意,我并不是说您的解决方案是错误的。这是OP的假设。
Gordon

27

数字和关联索引键之间没有关联。

当您说要使用键/值的数组索引设置关联数组的值时,则必须使用给定的键,设置$array[1]与setting不同$array['foo']

考虑这个数组

print_r( array('foo', 'foo' => 'bar', 'baz', 'some' => 'value') );

这将给

Array
(
    [0] => foo
    [foo] => bar
    [1] => baz
    [some] => value
)

foo是数组中的第二个元素。那是偏移量,但与索引1无关。如您所见,在上面的数组中,索引1与baz。仅仅因为foo是第一个关联键就与实际数字键1有任何关系是错误的。some不与2关联。

同样,对于如上所示的混合阵列,array_keys此站点上其他地方建议的解决方案将不起作用,因为

print_r( array_keys(array('foo', 'foo' => 'bar', 'baz', 'some' => 'value')) );

会给

Array
(
    [0] => 0
    [1] => foo
    [2] => 1
    [3] => some
)

因此,当您执行操作时,$array[$keys[1]]您实际上就是在做$array['foo']。但是,如果您要访问该数组('some')中的第二个关联值,则无法执行$array[$keys[2]],因为这将评估为$array[1]和的baz

元素的偏移与它的键或值完全无关

print_r(
    array(
        100    => 'foo',
        'foo'  => 'bar',
        50     => 'baz',
        'some' => 'value'
    )
);

真正意思

Array
( //key       value     offset/position
    [100]  => foo       // 0
    [foo]  => bar       // 1
    [50]   => baz       // 2
    [some] => value     // 3
)

这意味着偏移量为0的元素是foo,尽管其键为100。如果要按偏移量从数组中提取元素,则必须使用

$third = array_splice($array, 2, 1);
echo $third[0]; // baz

这将创建一个仅将元素保留在第三位置的数组。

或者您可以使用ArrayIterator。该ArrayIterator工具实现了一个Seekable接口,该接口使您可以查找数组中的特定位置/偏移,然后获取该位置/偏移:

$iterator = new ArrayIterator($array);
$iterator->seek(3);
echo $iterator->current(); // value

次要尼特: “如果你想访问数组中的第二个关联值(‘一些’),你不能做$阵列[$键[2],因为这将评估为$阵列[1],这就是巴兹” 从技术上讲,这是因为所有键(包括数字键)都是关联键-由返回的4个值array_keys。没有这样的实体作为“非关联密钥”。如果您想指出您不能返回第二个字符串键(假设键数组仅包含字符串),那么您所说的是正确的。$stringKeys = array_filter(array_keys($array), "is_string");提供字符串键。
ToolmakerSteve

17

虽然array_keys()允许访问第n个键,但array_values将为您提供第n个值。

<?php
$array = [
   0     => 'Zero',
   '1'   => 'One',
   'Two' => 'Two',
];
echo array_values($array)[2];
?>

将输出“ Two”。

有一个相对于另一个的优势吗?好吧,我唯一能看到的就是数组访问的次数。

随着array_keys()你需要3。

  1. 从数据数组中获取密钥。
  2. 从键列表中获取第n个键。
  3. 使用数据数组中的第n个键获取值。

使用array_values(),您只需要2。

  1. 从数据数组获取值。
  2. 从值列表中获取第n个值。

但是,另一方面,密钥通常较小,并且数据可能会大量嵌套,因此,总的来说,使用array_keys()可能更安全。


3

如果数组很大,则两者 array_keysarray_values将是浪费的,因为他们将分配一个新的数组大小相同,原来,只是为了让第n个键(或价值)。

array_slice接受整数偏移量,并在关联数组上工作。您可以使用它在恒定时间内获取(并设置)第n个键。

// This will at most allocate 2 temporary arrays of 1 element each
$key = array_keys(array_slice($array, $n, 1, true))[0];

$array[$key] = $value;

2
不错的解决方案!
大安

1

试试这个。它为您工作。

$result= array_values($my_arr); // Array with indexes you need

1
发布到已经有多个响应和一个可接受的答案的旧线程时,请小心。您需要解释为什么新答案比现有答案更好。
APC

0

另一种可能性是将其转换为普通数组:

$ arraybuff = implode(“ ~~~”,$ my_arr);
$ my_arr = explode(“ ~~~”,$ arraybuff);

其中“ ~~~”是定界符,不会在您的数据中出现。

现在,您可以使用等于偏移量的数字索引访问数组。

如果仍然需要保留关联数组,只需将其分配给其他变量。


由于您应该始终考虑,因此确切的定界符可能会出现在您的数据中,因此此想法仅适用于99.9999999%。有几种解决方案可以100%工作,此外,这将处理器设置为大量工作并浪费了内存,仅用于简单的阵列访问。
user426486
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.