Abstract trait't method not allowed to be stat

2019-06-23 17:02发布

Here is my example:

trait FileConfig {
    public static function getPathForUploads() {
        $paths = static::getPaths();
        //etc.
    }

    abstract public static function getPaths(); //doesn't work. Error: "Static function SharedDefaultConfig::getPaths() should not be abstract"

    abstract public function getPaths(); //OK
    public static function getPaths() {} //OK
}

Class:

class AppConfig {
    use FileConfig;

    public static function getPaths() {
        return array(...);  
    }
}

Call:

AppConfig::getPathForUploads();

It's nessessary to make it static and abstract (to force classes using FileConfig to implement getPaths).

I wonder how is it possible to implement method changing it's static property? Is it a good practice or there are better solutions? Will it one day become illegal?

Thank you

标签: php oop traits
3条回答
我只想做你的唯一
2楼-- · 2019-06-23 17:25

You do not need to make the method static to force classes using it to implement the method. You can simply use interfaces alongside.

trait FileUploadConfig {
    public static function getPathForUploads() {
        $paths = static::getPaths();
        //etc.
    }
}

The trait was left as is. I just took away the functions for the interface.

interface PathConfiguration {
    public static function getPaths();
}

The interface forces the class to implement the function. I left the static in there to correspond with the trait's specification.

class AppConfig implements PathConfiguration {
    use FileUploadConfig;
    public static function getPaths() {
        return [];
    }
}
查看更多
smile是对你的礼貌
3楼-- · 2019-06-23 17:34

To force classes using FileConfig to implement getPaths it's not nessessary to make abstract function static. Static means that it belongs to the class that declared it. Make it protected static, add code from trait and then you could change behaviour by inheritance from your AppConfig class.

查看更多
爱情/是我丢掉的垃圾
4楼-- · 2019-06-23 17:46

This is fixed in php 7, so the following code works:

<?php

error_reporting(-1);

trait FileConfig {
    public static function getPathForUploads() {
        echo static::getPaths();
    }

    abstract static function getPaths();
}

class AppConfig {
    use FileConfig;

    protected static function getPaths() {
        return "hello world";
    }
}

AppConfig::getPathForUploads();

http://sandbox.onlinephpfunctions.com/code/610f3140b056f3c3e8defb84e6b57ae61fbafbc9

But it does not actually check if the method in AppConfig is static or not during compilation. You will only get a warning when you try to call the non-static method statically: http://sandbox.onlinephpfunctions.com/code/1252f81af34f71e901994af2531104d70024a685

查看更多
登录 后发表回答