1


我有一个扩展 CComponent 的模型类

    class CompanyModel extends CComponent{ 
    private $company_pk;
    public function getCompany_pk()
   {
        return $this->company_pk;
   }
   public function setCompany_pk($value)    {
        $this->company_pk = $value;
    }
}

我有一个填充这个模态的函数

    public function getCompanyList() {
    $companyList=array();
    $company_obj = new CompanyModel();
    $sql = "SELECT company_pk,name FROM tbl_company WHERE status = ".Constants::ACTIVE_COMPANY;
    $command=$this->connection->createCommand($sql);
    $command->setFetchMode(PDO::FETCH_ASSOC);
    $rows=$command->queryAll();

    foreach ($rows as $row){
        $company_obj->company_pk = $row['company_pk'];
        array_push($companyList,$company_obj);

    }

    return $companyList;
}

和我的控制器

    Class UserController extends CController {
public  function actionGetCompanyList() {
    $model = new UserAction();
    $ret_val = $model->getCompanyList();
    echo CJSON::encode((array)$ret_val[0]);
         }
     }

我得到的 JSON 是

{"\u0000CompanyModel\u0000company_pk":"2"}

我怎样才能删除那些垃圾值

4

2 回答 2

1

我假设您以后无法解码它们,如果您更改$company_pk为 public 它应该正确编码。问题在于您的对象转换为数组,它将 NULL 字节添加到您的私有成员$company_pk。因为echo CJSON::encode((array)$ret_val[0]);它是对象数组。

你可以做坏事。

$json = '{"\u0000CompanyModel\u0000company_pk":"2"}';

$json = str_replace('\u0000', '', $json);

var_dump(json_decode($json));

或者您将对象传递给CJSON::encode我不太了解 YII,但它应该按照手册http://www.yiiframework.com/doc/api/1.1/CJSON处理对象。

这是重现问题的示例:

class test {
 private $private = 1;
 public $publiv = 2;
}

$obj = new test();
$array = (array) $obj;

$json = json_encode($array);

var_dump($json);

var_dump(json_decode($json));

编辑

从手册http://www.php.net/manual/en/language.types.array.php

如果将对象转换为数组,则结果是一个数组,其元素是对象的属性。键是成员变量名,有几个值得注意的例外:整数属性不可访问;私有变量在变量名前面加上类名;受保护的变量在变量名前有一个“*”。这些前置值在两边都有空字节。

CJSON::encode从 YII 快速查看了一下,你可以直接使用对象,但是你的对象必须是可遍历的,所以你必须实现 Iterator 接口。http://www.php.net/manual/en/class.iterator.php

编辑:2

实现接口可能很棘手,还有另一个选项可以get_object_vars从对象内调用,在这种情况下,您将获得可以工作的数组。

class CompanyModel extends CComponent
{
    private $company_pk;

    public function getCompany_pk()
    {
        return $this->company_pk;
    }
    public function setCompany_pk($value)
    {
        $this->company_pk = $value;
    }

    public function export()
    {
        return get_object_vars($this);
    }

}

接着:

$ret_val = $model->getCompanyList();
echo CJSON::encode($ret_val->export());

问题为什么它不适用于普通对象,因为 YII 在get_object_vars内部使用并且它在不同范围内时无法访问私有属性。

于 2013-06-15T11:13:24.453 回答
0

我发现如果我在模型类中扩展 CModel 而不是 CComponent,我可以实现我想要的。在扩展此类时,您将不得不重写一个抽象方法。否则会抛出错误。我的新模型类看起来像这样

   class CompanyModel extends CModel{ 
private $company_pk;
public function attributeNames()
{
    return array( 'company_pk' );
}

public function attributeLabels()
{
    return array( 'company_pk' => 'company_pk Label' );
}
public function getCompany_pk()
   {
    return $this->company_pk;
   }
public function setCompany_pk($value)    {
    $this->company_pk = $value;
}
}
于 2013-06-20T13:10:37.873 回答