PHP - 需要帮助将数组插入到给定键的关联数组中
Posted
技术标签:
【中文标题】PHP - 需要帮助将数组插入到给定键的关联数组中【英文标题】:PHP - Need help inserting arrays into Associative arrays at given keys 【发布时间】:2011-09-24 00:23:37 【问题描述】:好的,所以我有一个这样的数组:
$buttons = array(
'home' => array(
'title' => $txt['home'],
'href' => $scripturl,
'show' => true,
'sub_buttons' => array(
),
'is_last' => $context['right_to_left'],
),
'help' => array(
'title' => $txt['help'],
'href' => $scripturl . '?action=help',
'show' => true,
'sub_buttons' => array(
),
),
'search' => array(
'title' => $txt['search'],
'href' => $scripturl . '?action=search',
'show' => $context['allow_search'],
'sub_buttons' => array(
),
),
'admin' => array(
'title' => $txt['admin'],
'href' => $scripturl . '?action=admin',
'show' => $context['allow_admin'],
'sub_buttons' => array(
'featuresettings' => array(
'title' => $txt['modSettings_title'],
'href' => $scripturl . '?action=admin;area=featuresettings',
'show' => allowedTo('admin_forum'),
),
'packages' => array(
'title' => $txt['package'],
'href' => $scripturl . '?action=admin;area=packages',
'show' => allowedTo('admin_forum'),
),
'errorlog' => array(
'title' => $txt['errlog'],
'href' => $scripturl . '?action=admin;area=logs;sa=errorlog;desc',
'show' => allowedTo('admin_forum') && !empty($modSettings['enableErrorLogging']),
),
'permissions' => array(
'title' => $txt['edit_permissions'],
'href' => $scripturl . '?action=admin;area=permissions',
'show' => allowedTo('manage_permissions'),
'is_last' => true,
),
),
),
'moderate' => array(
'title' => $txt['moderate'],
'href' => $scripturl . '?action=moderate',
'show' => $context['allow_moderation_center'],
'sub_buttons' => array(
'modlog' => array(
'title' => $txt['modlog_view'],
'href' => $scripturl . '?action=moderate;area=modlog',
'show' => !empty($modSettings['modlog_enabled']) && !empty($user_info['mod_cache']) && $user_info['mod_cache']['bq'] != '0=1',
),
'poststopics' => array(
'title' => $txt['mc_unapproved_poststopics'],
'href' => $scripturl . '?action=moderate;area=postmod;sa=posts',
'show' => $modSettings['postmod_active'] && !empty($user_info['mod_cache']['ap']),
),
'attachments' => array(
'title' => $txt['mc_unapproved_attachments'],
'href' => $scripturl . '?action=moderate;area=attachmod;sa=attachments',
'show' => $modSettings['postmod_active'] && !empty($user_info['mod_cache']['ap']),
),
'reports' => array(
'title' => $txt['mc_reported_posts'],
'href' => $scripturl . '?action=moderate;area=reports',
'show' => !empty($user_info['mod_cache']) && $user_info['mod_cache']['bq'] != '0=1',
'is_last' => true,
),
),
),
'profile' => array(
'title' => $txt['profile'],
'href' => $scripturl . '?action=profile',
'show' => $context['allow_edit_profile'],
'sub_buttons' => array(
'summary' => array(
'title' => $txt['summary'],
'href' => $scripturl . '?action=profile',
'show' => true,
),
'account' => array(
'title' => $txt['account'],
'href' => $scripturl . '?action=profile;area=account',
'show' => allowedTo(array('profile_identity_any', 'profile_identity_own', 'manage_membergroups')),
),
'profile' => array(
'title' => $txt['forumprofile'],
'href' => $scripturl . '?action=profile;area=forumprofile',
'show' => allowedTo(array('profile_extra_any', 'profile_extra_own')),
'is_last' => true,
),
),
),
'pm' => array(
'title' => $txt['pm_short'],
'href' => $scripturl . '?action=pm',
'show' => $context['allow_pm'],
'sub_buttons' => array(
'pm_read' => array(
'title' => $txt['pm_menu_read'],
'href' => $scripturl . '?action=pm',
'show' => allowedTo('pm_read'),
),
'pm_send' => array(
'title' => $txt['pm_menu_send'],
'href' => $scripturl . '?action=pm;sa=send',
'show' => allowedTo('pm_send'),
'is_last' => true,
),
),
),
'calendar' => array(
'title' => $txt['calendar'],
'href' => $scripturl . '?action=calendar',
'show' => $context['allow_calendar'],
'sub_buttons' => array(
'view' => array(
'title' => $txt['calendar_menu'],
'href' => $scripturl . '?action=calendar',
'show' => allowedTo('calendar_post'),
),
'post' => array(
'title' => $txt['calendar_post_event'],
'href' => $scripturl . '?action=calendar;sa=post',
'show' => allowedTo('calendar_post'),
'is_last' => true,
),
),
),
'mlist' => array(
'title' => $txt['members_title'],
'href' => $scripturl . '?action=mlist',
'show' => $context['allow_memberlist'],
'sub_buttons' => array(
'mlist_view' => array(
'title' => $txt['mlist_menu_view'],
'href' => $scripturl . '?action=mlist',
'show' => true,
),
'mlist_search' => array(
'title' => $txt['mlist_search'],
'href' => $scripturl . '?action=mlist;sa=search',
'show' => true,
'is_last' => true,
),
),
),
'login' => array(
'title' => $txt['login'],
'href' => $scripturl . '?action=login',
'show' => $user_info['is_guest'],
'sub_buttons' => array(
),
),
'register' => array(
'title' => $txt['register'],
'href' => $scripturl . '?action=register',
'show' => $user_info['is_guest'],
'sub_buttons' => array(
),
'is_last' => !$context['right_to_left'],
),
'logout' => array(
'title' => $txt['logout'],
'href' => $scripturl . '?action=logout;%1$s=%2$s',
'show' => !$user_info['is_guest'],
'sub_buttons' => array(
),
'is_last' => !$context['right_to_left'],
),
);
现在我希望能够在上面数组中的任何键之前或之后插入一个数组。我要插入的数组可以是这样的:
$new_menu_buttons['testing'] = array(
'title' => $txt['testing'],
'href' => $scripturl . '?action=testing',
'show' => true,
'target' => '_self',
'active_button' => false,
);
有人推荐了处理这个问题的函数和使用方法,但我不知道该怎么做,他们也想要这些函数的偏移量。这是有人推荐我使用的函数结构,而不是在需要时调用这些函数:
function array_insert_before($array, $key, $new_array)
// Splice array in two at key, keeping key on the right side
// Append new value on the left tail
// Glue both arrays into a new array
// Return new array
function array_insert_after($array, $key, $new_array)
// Symmetric with right & left switched
所以,我希望能够像这样调用函数:
如果它需要在键之后,指定的'home':
$menu_buttons = array_insert_after($buttons, 'home', $new_menu_buttons);
如果它需要在键之前,指定的'home':
$menu_buttons = array_insert_before($buttons, 'home', $new_menu_buttons);
基本上,我真的需要这些功能的帮助,任何帮助都会很棒。
我应该使用array_splice
还是array_slice
?请问有人愿意用一些实际的代码让我朝着正确的方向开始吗?
谢谢大家:)
【问题讨论】:
在创建导航之前引入位置值并对其进行排序不是更容易吗?或者使用 SplHeap 或 PriorityQueue 来保持导航有序? 如果你觉得这个问题已经被回答了,那么你应该把它标记为已回答(检查评分下的按钮以获得答案)。 【参考方案1】:这应该可以帮助您入门。注意:我没有测试过这个。没想到吧。
/**
* This will insert $new at the beginning if $key is not found
*/
function array_insert_before($array, $key, $new)
$keys = array_keys($array);
$pos = (int) array_search($key, $keys);
return array_merge(
array_slice($array, 0, $pos),
$new,
array_slice($array, $pos)
);
array_insert_after()
几乎相同,除了$pos
加一。你应该能够自己弄清楚。
【讨论】:
@Sander Marechal - 您可以使用return array_splice($array, $position, 0, $new);
,而不是使用您的return array_merge(...)
调用。如果length
参数设置为0,它将插入offset
之后,其余部分保持不变。
你好 Sander,$key
总会被找到,因为这是来自同一个 $array 的键,它不是用户输入的。但它需要这样,因为我需要在创建数组之后在数组中执行此操作。谢谢会试一试,看看这是否对我有帮助。
SoLoGHoST - return array_merge(...)
调用了两次array_slice
,所以总共调用了 3 个函数。您可以将其替换为我在第一条评论中所写的内容(return array_splice(...)
)。为了回答您对@Sander Marechal 的评论,array_search
正在搜索数组中键的位置,而不是它是否存在。 array_slice
和 array_splice
都需要知道位置而不是密钥。
@SoLoGHoSt - 该行实际上应该包含return
。它应该在下一行返回(return $array
);另一件事是在上面@Sander Marechal 的代码中,array_search($keys, $key)
应该是array_search($key, $keys);
。
@Sander Marechal - array_splice
不起作用,我认为这是因为 array_splice
函数中的 replacement
参数不保留 $new
数组的键。你让它工作的方式完美,除了你应该有array_search($key, $keys;)
。我使用了你的方法,并在下面的答案中更好地适应了我的需要。【参考方案2】:
好的,在玩了一段时间之后,我终于让它按照我想要的方式工作了。我正在使用 $new_menu_buttons 中的某些键来决定要做什么。例如: position 告诉我它是在之后还是之前,parent 告诉我在哪里搜索键,slug 给我用于添加的每个新菜单数组的键。 array_splice
不适合我,所以我使用 array_merge
方法,效果很好。这是为其他遇到此问题的人准备的。
function array_insert_buttons($buttons, $new_menu_buttons)
foreach($new_menu_buttons as $new)
$keys = array_keys($buttons);
$position = (int)array_search($new['parent'], $keys);
if ($new['position'] == 'after')
$position = $position + 1;
// Create the new array in the correct format, using the slug!
$new_button = array();
$new_button[$new['slug']] = $new;
// Don't need these keys anymore.
unset($new_button[$new['slug']]['position']);
unset($new_button[$new['slug']]['parent']);
unset($new_button[$new['slug']]['slug']);
// Putting it all together now.
$buttons = array_merge(
array_slice($buttons, 0, $position),
$new_button,
array_slice($buttons, $position)
);
return $buttons;
感谢你们的帮助:)
【讨论】:
以上是关于PHP - 需要帮助将数组插入到给定键的关联数组中的主要内容,如果未能解决你的问题,请参考以下文章