出一道题

ice_berg16 2006-12-01 01:06:53
已经全局数组和一对存取函数

$config = array();
function set(){
}
function get(){
}


实现对$config数组的操作,

set("a.b.c", 123);
print_r(get());
//结果为
Array
(
[a] => Array
(
[b] => Array
(
[c] => 123
)

)

)
print_r(get("a.b.c"));
结果为 123

set函数
将给定的字符串"a.b.c"转换成$config的多级关联数组
get函数
有参数时返回对应的值
默认将返回整个$config数组

看看都有哪些算法.........
...全文
921 23 打赏 收藏 转发到动态 举报
写回复
用AI写文章
23 条回复
切换为时间正序
请发表友善的回复…
发表回复
Bevin_chen 2006-12-05
  • 打赏
  • 举报
回复
只能来接分了
lovexyyy 2006-12-05
  • 打赏
  • 举报
回复
mark!
kenesyu 2006-12-05
  • 打赏
  • 举报
回复
mark~
liany2023 2006-12-04
  • 打赏
  • 举报
回复
高手啊......
zeroleonhart 2006-12-02
  • 打赏
  • 举报
回复
function set($path, $value)
{
global $config;
$a = explode(',', $path);
$t = array($a[count($a)-1] => $value);
for($i = count($a)-2; $i>=0; $i--)
{
$t = array($a[$i] => $t);
}
$config = $t;
}

ice_berg16 2006-12-02
  • 打赏
  • 举报
回复
是第一种,覆盖
tony-杨 2006-12-02
  • 打赏
  • 举报
回复
还是要下面一样?
Array
(
[a] => Array
(
[b] => Array
(
[c] => array
(
[0] => 123
)
)
)
)
tony-杨 2006-12-02
  • 打赏
  • 举报
回复
set("a.b.c", 123);
//结果为
Array
(
[a] => Array
(
[b] => Array
(
[c] => 123
)
)
)
=====================
那如果set("a.b.c.d", 123);得到
Array
(
[a] => Array
(
[b] => Array
(
[c] => array
(
[d] => 123
)
)
)
)
这样是不是就要覆盖上以层的?
福贵 2006-12-01
  • 打赏
  • 举报
回复
功力不够,惭愧,too
ice_berg16 2006-12-01
  • 打赏
  • 举报
回复
不过
set("a.b", 123);
set("a.b.c", 345);产生...........这样的数组,应该也是允许的吧?
这样的话前面的还要改一下
if(!is_array($pt)) $pt = array();
=>
if(!is_array($pt) && isset($pt)) $pt = array($pt);
ice_berg16 2006-12-01
  • 打赏
  • 举报
回复
嗯。后面的算法和我的差不多

我这个主要是应用在快速存取一些配置信息上,我用了一个类来包装

class Config
{
//配置数组
static private $ini = array();

//禁止访问构造函数
private function __construct() {}

/**
* 更改配置信息
*
* 字符串可以使用set('dsn.driver','Mysql')的形式来设置子选项
*
* @param string|array $key 键名 可以是数组或字符串
* @return
*/
public static function set($key, $value=null)
{
if(is_array($key) && is_null($value))
self::$ini = array_merge(self::$ini, $key);
else
{
$arr = explode(".", $key);
$pt = &self::$ini;
while($arr)
{
if(!is_array($pt)) $pt = array();
$k = array_shift($arr);
$pt = &$pt[$k];
}
$pt = $value;
}
}

//取得配置信息
public static function get($key=null)
{
if(is_null($key)) return self::$ini;
$arr = explode(".", $key);
//用引用方式查找关联数组
$pt = &self::$ini;
while($arr)
{
if(!is_array($pt)) return null;
$k = array_shift($arr);
$pt = &$pt[$k];
}
return $pt;
}

//载入配置文件或配置数组
public static function load($ini)
{
if(is_array($ini))
self::$ini = $ini;
else
{
if(!file_exists($ini))
throw new Exception(sprintf("配置文件不存在 -> <span class='red'>%s</span>",$ini));
self::$ini = require_once($ini);
}

}

}
Config::set("a", 'test');
Config::set("c.d.e.f", 123);
Config::set("c.d.e", array(1,2,3));
print_r(Config::get());
xuzuning 2006-12-01
  • 打赏
  • 举报
回复
使用eval同样能保证“get一个不存在的键值会返回NULL”
var_dump(get("a.b.c.p")); //out NULL

而满足:
set("a.b", 123);
set("a.b.c", 345);
操作是合法的,后面的操作会覆盖前面的,
则需要
function set($path, $value) {
global $config;
$p = explode('.', $path);
$t =& $config;
foreach($p as $k) {
if(!is_array($t[$k])) $t[$k] = array();
$t =& $t[$k];
}
$t = $value;
}

不过
set("a.b", 123);
set("a.b.c", 345);
若产生
Array
(
[a] => Array
(
[b] => Array
(
[0] => 12
[c] => 123
)
)
)
这样的数组,应该也是允许的吧?
不过楼主并没有详细描述他的需求。
xuzuning 2006-12-01
  • 打赏
  • 举报
回复
to jinliangonline(水清无鱼)
把你的 set() 补全
function set($path, $value) {
global $config;
$p = explode('.', $path);
$t =& $config;
foreach($p as $k) {
if(!isset($t[$k])) $t[$k] = array();
$t =& $t[$k];
}
$t = $value;
}
ice_berg16 2006-12-01
  • 打赏
  • 举报
回复
set("a.b.c", 123);
//不明白为什么会出那样的结果,形参有固定吗?再举多个例子吧
后面已经说了
将给定的字符串"a.b.c"转换成$config的多级关联数组
就是说会生成
$config['a']['b']['c'] = 123;这样的数组

需要说明的是
set函数有覆盖性

set("a.b", 123);
set("a.b.c", 345);
操作是合法的,后面的操作会覆盖前面的,
而get一个不存在的键值会返回NULL,

get("a.b.e.f") = null;
并不会报错

我开始也想到了EVAL,但是我上面提到的两个要求用EVAL就比较困难,
而且eval让代码很难看懂,用引用的办法解决了。
我的写法下班的时候贴,想看看都有什么思路,
echo_php 2006-12-01
  • 打赏
  • 举报
回复
功力不够啊,惭愧
jinliangonline 2006-12-01
  • 打赏
  • 举报
回复
老大发话了,我就耍一回,数组学的不好,写写想法:
function set($path, $value) {
分割$path,写入数组array,然后array_push($array,$value)
根据count($array)循环写入新的多维数组。//卡在这了????
}
function get($path='') {
global $config;
if(empty($path)) return $config;
else{直接返回多位数组的最后一维的值。(可根据$path的个数判断此数组是几维)}
}
xuzuning 2006-12-01
  • 打赏
  • 举报
回复
我的写法并不是最好的,把你的贴出来嘛
jinliangonline 2006-12-01
  • 打赏
  • 举报
回复
强,学习了,刚想耍大刀呢,幸亏刷新了下回复。
xuzuning 2006-12-01
  • 打赏
  • 举报
回复
$config = array();

function set($path, $value) {
global $config;
$p = str_replace('.', "']['", $path);
eval("\$config['$p'] = \$value;");
}

function get($path='') {
global $config;
if(empty($path)) return $config;
$p = str_replace('.', "']['", $path);
return eval("return \$config['$p'];");
}

set("a.b.c", 123);
print_r(get());
print_r(get("a.b.c"));
willko 2006-12-01
  • 打赏
  • 举报
回复
set("a.b.c", 123);
//不明白为什么会出那样的结果,形参有固定吗?再举多个例子吧
加载更多回复(3)

21,886

社区成员

发帖
与我相关
我的任务
社区描述
从PHP安装配置,PHP入门,PHP基础到PHP应用
社区管理员
  • 基础编程社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧