Giả sử có một Page
lớp, đại diện cho một bộ hướng dẫn cho trình kết xuất trang. Và giả sử có một Renderer
lớp biết cách kết xuất một trang trên màn hình. Có thể cấu trúc mã theo hai cách khác nhau:
/*
* 1) Page Uses Renderer internally,
* or receives it explicitly
*/
$page->renderMe();
$page->renderMe($renderer);
/*
* 2) Page is passed to Renderer
*/
$renderer->renderPage($page);
Những ưu và nhược điểm của từng phương pháp là gì? Khi nào một người sẽ tốt hơn? Khi nào thì người kia sẽ tốt hơn?
LÝ LỊCH
Để thêm một chút nền tảng - tôi thấy mình sử dụng cả hai cách tiếp cận trong cùng một mã. Tôi đang sử dụng thư viện PDF của bên thứ 3 được gọi TCPDF
. Ở đâu đó trong mã của tôi, tôi phải có các phần sau để kết xuất PDF hoạt động:
$pdf = new TCPDF();
$html = "some text";
$pdf->writeHTML($html);
Nói rằng tôi muốn tạo một đại diện của trang. Tôi có thể tạo một mẫu chứa các hướng dẫn để hiển thị đoạn trích trang PDF như sau:
/*
* A representation of the PDF page snippet:
* a template directing how to render a specific PDF page snippet
*/
class PageSnippet
{
function runTemplate(TCPDF $pdf, array $data = null): void
{
$pdf->writeHTML($data['html']);
}
}
/* To be used like so */
$pdf = new TCPDF();
$data['html'] = "some text";
$snippet = new PageSnippet();
$snippet->runTemplate($pdf, $data);
1) Lưu ý ở đây là $snippet
tự chạy , như trong ví dụ mã đầu tiên của tôi. Nó cũng cần phải biết và làm quen với $pdf
, và với bất kỳ $data
để nó hoạt động.
Nhưng, tôi có thể tạo một PdfRenderer
lớp như vậy:
class PdfRenderer
{
/**@var TCPDF */
protected $pdf;
function __construct(TCPDF $pdf)
{
$this->pdf = $pdf;
}
function runTemplate(PageSnippet $template, array $data = null): void
{
$template->runTemplate($this->pdf, $data);
}
}
và sau đó mã của tôi chuyển sang đây:
$renderer = new PdfRenderer(new TCPDF());
$renderer->runTemplate(new PageSnippet(), array('html' => 'some text'));
2) Ở đây $renderer
nhận được PageSnippet
và bất kỳ $data
yêu cầu cho nó để làm việc. Điều này tương tự với ví dụ mã thứ hai của tôi.
Vì vậy, mặc dù trình kết xuất nhận được đoạn mã trang, bên trong trình kết xuất, đoạn mã vẫn tự chạy . Đó là để nói rằng cả hai cách tiếp cận đang chơi. Tôi không chắc chắn nếu bạn có thể hạn chế sử dụng OO của bạn chỉ một hoặc chỉ một. Cả hai có thể được yêu cầu, ngay cả khi bạn che dấu cái khác.