Лучший способ использовать класс внутри другого класса

0

Я создал этот класс, который извлекает все данные записи из базы данных.

class Post {
    private $id;
    protected $conn;
    public $data;

    function __construct(\mysqli $conn) {
        $this->conn = $conn;
    }

    public function getId() {
        return $this->id;
    }

    public function getConnection() {
        return $this->conn;
    }

    public function getPost() {
        $query1 = $this->getConnection()->query("SELECT * FROM posts WHERE id=" . $this->id);

        if ($query1->num_rows == 1) {
            $this->data = $query1->fetch_object();
            return $this->data;
        }
    }

    public function setId($id) {
        $this->id = (int)$id;
    }
}

Наряду с сообщением мне также нужно получить все данные пользователя, создавшего сообщение. У меня есть три способа сделать это:

1) Вызов класса User внутри класса Post.

    public function getPost() {
        $query1 = $this->getConnection()->query("SELECT * FROM posts WHERE id=" . $this->id);

        if ($query1->num_rows == 1) {
            $this->data = $query1->fetch_object();

            // Initiating User class
            $user = new User($this->getConnection());
            $user->setUserId($this->data->user_id);
            $this->data->user = $user->getUserInfo();

            return $this->data;
        }
    }


2) Расширяя класс Post с классом User.

class Post extends User {
    ....

Затем вызов методов из класса User

    public function getPost() {
        $query1 = $this->getConnection()->query("SELECT * FROM posts WHERE id=" . $this->id);

        if ($query1->num_rows == 1) {
            $this->data = $query1->fetch_object();

            // Calling methods from the User class
            $this->setUserId($this->data->user_id);
            $this->data->user = $this->getUserInfo();

            return $this->data;
        }
    }


3) Создав пользовательский признак и используя его в классе Post.

class Post {
    use UserTrait;
    ....

Затем вызов методов из пользовательской черты

    public function getPost() {
        $query1 = $this->getConnection()->query("SELECT * FROM posts WHERE id=" . $this->id);

        if ($query1->num_rows == 1) {
            $this->data = $query1->fetch_object();

            // Calling methods from the User trait
            $this->setUserId($this->data->user_id);
            $this->data->user = $this->getUserInfo();

            return $this->data;
        }
    }


Между этими 3, какой из них лучше всего подходит с точки зрения инъекции зависимостей, производительности и чистоты кода?

Теги:
class
dependency-injection
oop
traits

3 ответа

0
Лучший ответ

Этот вопрос может быть опущен до ада, потому что вы запрашиваете мнение, но я брошу свои два цента.

Вы в основном создаете свой собственный ORM. В этой ORM вы имеете дело с сущностями. Различные объекты должны обрабатываться разными классами (Модели), и должна быть эквивалентность 1:1 между базой данных БД и Моделью.

Существуют отношения между вашими сущностями. У объекта Yous Post есть автор, который должен быть экземпляром объекта User. Тем не менее, вы не сказали бы, что связь между почтовой таблицей и таблицей пользователя означает, что они могут быть представлены одной и той же моделью или разными вариантами родительской модели.

Если вы использовали полную ORM (Doctrine, Propel, RedbeanPHP), вы увидите, что такое отношение, как автор Post, означает, что при использовании таких методов, как getById() (в вашем случае getPost()), полученный объект сообщения будет продолжать экземпляр каждого зависимого объекта по умолчанию.

В вашем случае вместо $this->data->user_id ORM предложит вам вложенный $this->data->user объект $this->data->user поэтому вам не придется иметь дело с этим самостоятельно.

Итак, если вы слишком рано считаете, что используете ORM, первый подход легче выполнять и переносить, когда придет время.

Несвязанное мнение

На этом этапе, чтобы получить информацию о сообщении, вам нужно сделать

$post = new Post($conn);
$post->setId($postid);
$postdata = $post->getPost();

Если вы изменили свой конструктор и добавили метод getById(), чтобы

function __construct(\mysqli $conn) {
    $this->conn = $conn;
    return $this;
}

public function getById($id) {
     $this->setId($id);
     return $this->getPost();
}

вы могли бы вместо этого получить данные сообщения в одной строке

$postdata=(new Post($conn))->getById($postid);
  • 0
    Большое вам спасибо @amenadiel
0

Я думаю, это зависит от других аспектов вашего кода. Лично я бы просто расширил класс User, поскольку я не думаю, что в этом конкретном случае необходимо использовать черты.

Здесь есть полезная статья об использовании Traits в PHP - Использование признаков в PHP 5.4

0

Все зависит от того, что вы собираетесь продолжать делать. С расширенным классом лучше справиться, если вы собираетесь использовать постоянные методы других классов. Если вам нужна только часть другого класса, просто вызовите класс и его метод.

ОСТОРОЖНО: расширенный класс ведет себя как один класс. Здесь может быть много столкновений, если у вас одинаковые имена методов и функций.

Ещё вопросы

Сообщество Overcoder
Наверх
Меню