Home  >  Article  >  Backend Development  >  Clever overloading of magic method __call(), overloading magic __call_PHP tutorial

Clever overloading of magic method __call(), overloading magic __call_PHP tutorial

WBOY
WBOYOriginal
2016-07-13 10:09:58741browse

Ingenious overloading magic method __call(), overloading magic __call

I have been working for half a year, and I feel that I have learned more in this half year than in four years of college. More. The main reason is that my mind calms down, my goals are clear, and I no longer get entangled with games all day long. When I was in college, I actually realized that playing games would affect my normal study and work, but I couldn't control myself. I still couldn't help but play often, day and night (I was originally a sultry guy, and I still stayed at home playing games. , this is also one of the reasons why I only had games, left and right hands, and no girlfriends during the four years of college). Now that I am working, I have tasks every day. When I see the talented people next to me working on the project like a duck to water, I have the idea of ​​catching up with them, so I give myself an extra small task every day to learn new knowledge. I have been working for half a year now. Now I can use Linux which I was not familiar with before. I also have a new understanding of JS which I am not familiar with. It can be said that I am competent at the job now (if divided into novice, advanced novice, competent and proficient) , experts), have developed activities, interfaces, and backends, and have also optimized and improved the system framework. As long as there are reasonable needs raised by product operations, they can be quickly supported. Of course, I really feel one thing: Programmers are really a strange group. Most of the time, they always think that their own ideas are the best. Of course, this is considered self-confidence, but sometimes your aggressiveness during discussions is not necessarily a good thing, so you should listen to other people’s ideas. Not only can you discover your own shortcomings, but you can also build good friendships: " ". I’ve been telling you so much about my feelings over the past six months, thank you for sticking with me and reading it^_^.

Now let’s step into the real question and talk about how to skillfully use PHP’s magic method. I believe this will be used in most projects.

Let me explain first, I have already used this little trick very well in my project, and it has brought great convenience to our project. I will give you some details here, you may wish to continue reading.

In the project, there must be a large amount of configuration information that can be configured, such as the robot opening time period of a game, whether the payment method is enabled, the configuration of the title display in the mall, etc. One characteristic of these configuration information is that it does not exist. Specific rules, and product operations can be modified at any time according to the actual situation. How to save this information? It is definitely not possible to build a table for each type. This is simply thankless. If you think about it, maybe one There is only one piece of information saved in the table, so you have to think of other methods. Although there are no rules for this information, they have a characteristic that there will not be too much, and generally an array can save all the information that needs to be configured, so use JSON string storage information is a good choice. When you need to use it, just take out the json_decode and you can use it directly. Let’s take a look at how to cleverly use PHP’s magic method to achieve it.

Here you first need to understand __call(), a magic method of PHP. Check the official PHP documentation, which explains this function like this

<span>public</span> <span>mixed</span> __call ( <span>string</span> <span>$name</span> , <span>array</span> <span>$arguments</span><span> )

__call() is triggered when invoking inaccessible methods in an </span><span>object</span> context.

It means that this function will be triggered when an inaccessible method (no permission, non-existence) is called in an object. The parameter $name of the function is the name of the called function, and $arguments is the parameter array of the called function. Take a look at this example:

<span>class</span><span> Test
{
    </span><span>public</span> <span>function</span> __call(<span>$name</span>, <span>$arguments</span><span>)
    {
        </span><span>echo</span> "你调用了一个不存在的方法:\r"<span>;
        </span><span>echo</span> "函数名:{<span>$name</span>}\r"<span>;
        </span><span>echo</span> "参数: \r"<span>;
        </span><span>print_r</span>(<span>$arguments</span><span>);
    }
}

</span><span>$T</span> = <span>new</span><span> Test();
</span><span>$T</span>->setrobottime("12", "18");

This function will output the following results

<span>你调用了一个不存在的方法:
函数名:setrobottime
参数: 
Array
(
    [</span>0] => 12<span>
    [</span>1] => 18<span>
)</span>

In this way, we can not directly define the function, but use this feature to do something. Let’s take a look at the implementation ideas of the code. The main ideas are the ideas. Some of them are assumptions, such as database connections. I won’t focus on this here.

<span>class</span><span> Config
{
    </span><span>/*</span><span>*
     * 这里假定下数据库表名为
     * config.config,
     * 字段为:
     * config_key varchar(50),
     * config_value text,
     * primary key(config_key)
     *
     * 数据库连接为$link
     * 插入方法封装为query
     * 获取一条信息方法封装为getOne
     </span><span>*/</span>
    <span>/*</span><span>*
     * 要进行的操作
     </span><span>*/</span>
    <span>private</span> <span>static</span> <span>$keys</span> = <span>array</span><span>(
        </span><span>//</span><span>'调用方法' => 'key',</span>
        'roboottime'    => 'ROBOOTTIME',
        'dailysignin'   => 'DAILYSIGNIN',<span>
    );

    </span><span>/*</span><span>*
     * 设置方法
     * @param string $config_key 配置项key
     * @param string $config_value 配置型内容(一般为json格式)
     * @returne boolen true/false 插入是否成功
     </span><span>*/</span>
    <span>private</span> <span>function</span> set(<span>$config_key</span>, <span>$config_value</span><span>){
        </span><span>$sql</span> = "insert into config.config (config_key,config_value) values ('{<span>$config_key</span>}','{<span>$config_value</span>}') on duplicate key update config_value='{<span>$config_value</span>}'"<span>;
        </span><span>return</span> <span>$link</span>->query(<span>$sql</span><span>);
    }

    </span><span>/*</span><span>*
     * 获取值的方法
     * @param $config_key 要获取的配置的key
     * @returne string/false json字符串/失败
     </span><span>*/</span>
    <span>private</span> <span>function</span> get(<span>$config_key</span><span>)
    {
        </span><span>$sql</span> = "select * from config.config where config_key='{<span>$config_key</span>}'"<span>;
        </span><span>if</span>(<span>$ret</span> = <span>$link</span>->getOne(<span>$sql</span>,<span> MYSQL_ASSOC)){
            </span><span>return</span> <span>$ret</span><span>;
        }
        </span><span>return</span> <span>false</span><span>;
    }

    </span><span>/*</span><span>*
     * 重载魔术方法
     * @param string $name 被调用的方法名
     * @param array $arguments 调用时传递的参数
     * @return mixed 返回结果
     </span><span>*/</span>
    <span>public</span> <span>function</span> __call(<span>$name</span>, <span>$arguments</span><span>)
    {
        </span><span>$act</span>    = <span>substr</span>(<span>$name</span>, 0, 3<span>);
        </span><span>$func</span>   = <span>substr</span>(<span>$name</span>, 3<span>);
        </span><span>if</span>(!<span>in_array</span>(<span>$func</span>, self::<span>$keys</span><span>)){
            </span><span>return</span> <span>false</span><span>;
        }
        </span><span>if</span>(<span>$act</span> == 'set'<span>)
        {
            </span><span>return</span> <span>$this</span>->set(self::[<span>$func</span>], <span>$arguments</span>[0<span>]);
        }
        </span><span>elseif</span>(<span>$act</span> == 'get'<span>)
        {
            </span><span>return</span> <span>$this</span>->get(self::[<span>$func</span><span>]);
        }
        </span><span>return</span> <span>false</span><span>;
    }
}</span>

In this way, we can store multiple information through one table, and it is also very convenient when calling. We only need to expand the information in the Config::$keys array. This is just for standardization and to make it possible Clearly know which configurations are stored in this table.

When using it, you can store and retrieve it like this

<span>$config</span> = <span>new</span><span> Config();

</span><span>$info</span> = <span>array</span>("12","20"<span>);

</span><span>//</span><span>设置</span>
<span>$config</span>->setroboottime(json_encode(<span>$info</span><span>));

</span><span>//</span><span>获取</span>
<span>$config</span>->getroboottime();

Here is another point to note. These configuration information are generally cached in redis. They are placed in the database just to prevent recovery from the database after redis hangs. The ones here generally refer to those that are frequently read. Information, in order to reduce interaction with the db, is placed directly in the cache.

Clever overloading of magic method __call(), overloading magic __call_PHP tutorial The copyright of this article belongs to the author iforever (luluyrt@163.com). Any form of reprinting is prohibited without the consent of the author. After reprinting the article, the author and the original text link must be given in an obvious position on the article page, otherwise we will reserve the right to pursue it. Legal liability rights.

www.bkjia.comtruehttp: //www.bkjia.com/PHPjc/940335.htmlTechArticleIngenious overloading magic method __call(), overloading magic __call. I have been working for half a year, and I feel like I have learned a lot in this half year. I learned more than I learned in four years of college. The main reason is that my mind calmed down and my goals...
Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn