php-cpp扩展类arrayaccess返回自引用

时间:2014-12-26 11:23:17

标签: php c++ php-cpp

我在php中使用自定义扩展程序时遇到问题。 我正在为自制对象扩展Php :: ArrayAccess,并且我能够在PHP juste中使用我的对象,就像本机数组一样。但即使我在offsetGet的实现中返回对象的引用,我也无法链接运算符[]。我收到这个错误:

PHP致命错误:无法使用Jq类型的对象作为...中的数组(第0行的myfile.php)

#include <phpcpp.h>
#include <iostream>
#include <sstream>
#include <algorithm>

class Jq : public Php::Base, public Php::ArrayAccess
{
public:
  Jq()
  {
  }

  virtual ~Jq()
  {
  }

  void __construct(Php::Parameters& params)
  {
    std::string localParam1 = params[0];
    std::string localParam2 = params[1];

    _pathToJq = localParam1;
    _pathToCacheFile = localParam2;
  }

  Php::Value __toString()
  {
    return asString();
  }

  Php::Value asString()
  {
    std::ostringstream os;

    os << _pathToJq << ' ' << _pathToCacheFile << " : " << _filters.str();
    return os.str();
  }

  virtual bool offsetExists(const Php::Value &key) override
  {
    return true;
  }

  virtual Php::Value offsetGet(const Php::Value& key) override
  {
    return &((*this)[key]);
  }

  virtual void offsetSet(const Php::Value &key, const Php::Value &value) override
  {

  }

  virtual void offsetUnset(const Php::Value &key) override
  {

  }

  Jq& operator[] (const std::string& key)
  {
    const std::string offset = key;

    if (is_number(offset)) {
      if (_filters.tellp() > 0) {
    _filters << '[' << offset << ']';
      } else {
    _filters << ".[" << offset << ']';
      }
    } else {
      _filters << '.' << offset;
    }

    return *this;
  }

private:
  std::string       _pathToJq;
  std::string       _pathToCacheFile;
  std::ostringstream    _filters;
  std::ostringstream    _chainedOutput;

  bool is_number(const std::string& s)
  {
    return !s.empty() && std::find_if(s.begin(), s.end(), [](char c) { return !std::isdigit(c); }) == s.end();
  }
};

/**
 *  tell the compiler that the get_module is a pure C function
 */
extern "C" {
    /**
     *  Function that is called by PHP right after the PHP process
     *  has started, and that returns an address of an internal PHP
     *  strucure with all the details and features of your extension
     *
     *  @return void*   a pointer to an address that is understood by PHP
     */
    PHPCPP_EXPORT void *get_module() 
    {
        // static(!) Php::Extension object that should stay in memory
        // for the entire duration of the process (that's why it's static)
        static Php::Extension extension("jq", "0.0.1");

        // @todo    add your own functions, classes, namespaces to the extension
    Php::Class<Jq> jq("Jq");

    jq.method("__construct", &Jq::__construct);
    jq.method("__toString", &Jq::__toString);
    jq.method("asString", &Jq::asString);
    //jq.method("offsetGet", &Jq::offsetGet);

    // add the class to the extension
    extension.add(std::move(jq));

        // return the extension
        return extension;
    }
}

和要执行的php代码:

<?php

$jqa = new Jq("pathJQ", "pathCache");
// This is fine !
echo $jqa['test'] . PHP_EOL;
// This is fine too !
echo $jqa . PHP_EOL;
// But This is not !
echo $jqa['coc']['players'][0]['name'] . PHP_EOL;

感谢您的帮助!

0 个答案:

没有答案