以高效且可读的方式声明属性和变量?

Declaring properties and variables in an efficient and readable way?

首先,我想说明这是一个效率和 "coding preference" 问题 -- 不是逻辑或语法问题。

我正在尝试为我的数据库交互和逻辑构建一个 class。在这个 class 中,我发现自己 "defining" 同一组变量三次(在 [Area 1][Area 2][Area 3] 中)。

这似乎是多余的且具有误导性——一定有更好的做事方式,对吗?

目前,我的代码如下所示:

class db_connection {

   // [Area 1] define properties
   private $db_server;
   private $db_user;
   private $db_password_file;
   private $db_name;

   public function __construct() {
      // [Area 2] give each property a value based on environment variables
      $this->db_server = getenv( 'DB_HOST' );
      $this->db_user = getenv( 'DB_USER' );
      $this->db_password_file = getenv( 'DB_PASSWORD_FILE' );
      $this->db_name = getenv( 'DB_NAME' );
   }

   // create a function to perform connection logic
   public function connect() {

      // [Area 3] give each property a "labeling" variable for readability and ease-of-use
      $db_server = $this->db_server;
      $db_user = $this->db_user;
      $db_password_file = $this->db_password_file;
      $db_name = $this->db_name;

      [...]

这是我在我的三个 "Areas" 中的每一个 "defining" 的推理:

[区域 1]
在 class 定义的顶部声明属性是标准做法。通常,这些属性也会被初始化(使用值),但这在这里是不可能的,因为我想使用 getenv() 为这些属性分配非常量值。有关详细信息,请参阅 documentation

[区域 2]
按照 [Area 1] 的逻辑,我使用 class 构造函数初始化我的属性。

[区域 3]
为了保持我的连接逻辑清晰,我给了我的每个属性一个本地 "labeling" 变量。我在其余代码中更多地使用这些属性,因此使用 $db_user$this->db_user 这样的名称可以使事情变得更容易和更具可读性。


这似乎有很多代码只需要 4 properties/variables...

有没有更好的组织方式?我应该做些什么不同的事情?

能否在某处定义常量,或使用 static 关键字帮助?

在您的情况下,如果 db_serverdb_userdb_password_file 不会在运行时动态更改,您最好定义为 constant 而不是 property以获得更高效的性能。

正如您提到的,它们是通过 getenv() 函数从 .env 文件中读取的。是的,预定义常量或属性不能调用函数或表达式。如果我是你,我会在构建时创建连接。

class DBConnection 
{

    /**
     * Connection object
     */
    private $connection;

    /**
     * Construct
     */
    public function __construct() 
    {
        // Create a db connection assign to $this->connection
        $this->connection = new PDO(getenv('DB_HOST'), getenv('DB_USER'), ......);
    }

    /**
     * Get all users
     */
    public function getUser()
    {
        return $this->connection->query("SELECT * FROM USER");
    }

}


/**
 * New an instance of DBConnection
 * After that, they are all prepared.
 */
$database = new DBConnection;

/**
 * Call that function to get all users.
 */
$database->getUser();

区域 1 和 2 看起来不可避免。他们必须是完成该任务的人。

区域3,但是,您可以使用一个技巧。您可以使用以下命令使用本地等效项轻松定义所有 class 变量:

extract(get_object_vars($this));

这里发生的事情是 get_object_vars() returns 指定对象上定义的所有变量的数组。在本例中,我们的目标是 $this,即 class 实例。它将提供所有定义的 class 变量的数组,然后在传递给 extract().

时创建为本地副本

如果这些 class 变量的值需要更改,这样做的好处是可以干净利落地工作。否则,使用常量可能更漂亮。