複数のキャンバスをPDFに保存したい(TCanvas::Print)
1#include <TCanvas.h>
2#include <TH1D.h>
3
4// ファイル名を設定
5TString filename = "output.pdf";
6
7// キャンバスを作成
8TCanvas *c = new TCanvas("c", "Multi-page PDF", 800, 600);
9
10// PDFファイルを開く(最初のページ)
11c->Print(filename + "[", "pdf");
12
13// 複数のヒストグラムを描画して保存
14for (Int_t i = 0; i < 3; i++) {
15 TH1D *h = new TH1D(Form("h%d", i), Form("Histogram %d", i), 100, -3, 3);
16 h->FillRandom("gaus", 1000);
17 h->Draw();
18
19 // PDFにページを追加
20 c->Print(filename, "pdf");
21}
22
23// PDFファイルを閉じる
24c->Print(filename + "]", "pdf");
TCanvas::Printメソッドを使って、複数のページを1つのPDFファイルに保存できます。
PDF形式ではページ開始記号[と終了記号]を使うことで、複数のキャンバスを同じファイルに追記できます。
1from ROOT import TCanvas, TH1D
2
3filename = "output.pdf"
4
5c = TCanvas("c", "Multi-page PDF", 800, 600)
6
7# PDFファイルを開く
8c.Print(filename + "[", "pdf")
9
10# 複数のページを追加
11for i in range(3):
12 h = TH1D(f"h{i}", f"Histogram {i}", 100, -3, 3)
13 h.FillRandom("gaus", 1000)
14 h.Draw()
15 c.Print(filename, "pdf")
16
17# PDFファイルを閉じる
18c.Print(filename + "]", "pdf")
メソッドのシグネチャ
1void Print(const char *filename = "", Option_t *option = "")
引数と戻り値
引数:
filename - 出力ファイルパス。PDFマルチページの場合:
filename + "["- PDFファイルを開く(最初のページ)filename- PDFにページを追加filename + "]"- PDFファイルを閉じる
option - 出力形式(
"pdf"、"ps"など)
PDFマルチページの基本パターン
ページ開始・追加・終了の記号
記号 |
説明 |
使用例 |
|---|---|---|
|
PDFファイルを開く(最初のページは出力しない) |
|
(通常) |
現在のキャンバスをページとして追加 |
|
|
PDFファイルを閉じる |
|
記号の重要性
[を使わないと、その時点でページが出力される]を使うことで、PDFファイルが確実に閉じられる複数の
[と]を使うと、エラーが発生する可能性がある
使用例
複数のヒストグラムを1つのPDFに保存したい
1#include <TCanvas.h>
2#include <TH1D.h>
3#include <TRandom.h>
4
5TCanvas *c = new TCanvas("c", "Analysis Results", 800, 600);
6
7TString filename = "analysis.pdf";
8
9// PDFファイルを開く
10c->Print(filename + "[", "pdf");
11
12// 複数のヒストグラムを描画して保存
13for (Int_t i = 0; i < 5; i++) {
14 TH1D *h = new TH1D(Form("h%d", i), Form("Dataset %d", i), 100, -5, 5);
15
16 // ガウス分布でデータを埋める
17 for (Int_t j = 0; j < 10000; j++) {
18 h->Fill(gRandom->Gaus(0, 1));
19 }
20
21 h->Draw();
22 c->Print(filename, "pdf"); // ページを追加
23}
24
25// PDFファイルを閉じる
26c->Print(filename + "]", "pdf");
複数のヒストグラムを順番に描画し、各々をPDFの新しいページとして保存します。
複数のキャンバスから異なるオブジェクトを保存したい
1#include <TCanvas.h>
2#include <TGraph.h>
3#include <TH2D.h>
4
5TString filename = "mixed_objects.pdf";
6
7// 1番目のキャンバス:ヒストグラム
8TCanvas *c1 = new TCanvas("c1", "Canvas 1", 800, 600);
9c1->Print(filename + "[", "pdf");
10
11TH1D *h = new TH1D("h", "Histogram", 100, -3, 3);
12h->FillRandom("gaus", 5000);
13h->Draw();
14c1->Print(filename, "pdf");
15
16// 2番目のキャンバス:グラフ
17TCanvas *c2 = new TCanvas("c2", "Canvas 2", 800, 600);
18TGraph *g = new TGraph();
19for (Int_t i = 0; i < 100; i++) {
20 g->SetPoint(i, i, sin(i * 0.1));
21}
22g->Draw("AL");
23c2->Print(filename, "pdf");
24
25// 3番目のキャンバス:2次元ヒストグラム
26TCanvas *c3 = new TCanvas("c3", "Canvas 3", 800, 600);
27TH2D *h2 = new TH2D("h2", "2D Histogram", 50, -3, 3, 50, -3, 3);
28for (Int_t i = 0; i < 10000; i++) {
29 h2->Fill(gRandom->Gaus(), gRandom->Gaus());
30}
31h2->Draw("colz");
32c3->Print(filename, "pdf");
33
34// PDFファイルを閉じる
35c3->Print(filename + "]", "pdf");
異なるキャンバスや異なるオブジェクト(ヒストグラム、グラフ、2次元ヒストグラムなど)を同じPDFに保存できます。
ループで大量のページを生成したい
1#include <TCanvas.h>
2#include <TH1D.h>
3#include <TRandom.h>
4
5TString filename = "large_pdf.pdf";
6TCanvas *c = new TCanvas("c", "Large PDF", 800, 600);
7
8c->Print(filename + "[", "pdf");
9
10// 100ページ分のヒストグラムを生成
11for (Int_t page = 0; page < 100; page++) {
12 TH1D *h = new TH1D(Form("h%d", page),
13 Form("Page %d - Distribution", page),
14 100, -5, 5);
15
16 // 異なる平均値でデータを生成
17 Double_t mean = -5 + page * 0.1;
18 for (Int_t i = 0; i < 5000; i++) {
19 h->Fill(gRandom->Gaus(mean, 1));
20 }
21
22 h->Draw();
23 c->Print(filename, "pdf");
24
25 // メモリ管理:前のヒストグラムを削除
26 delete h;
27}
28
29c->Print(filename + "]", "pdf");
30
31std::cout << "PDF file created: " << filename << std::endl;
ループを使って大量のページを効率的に生成できます。 メモリ管理を適切に行うことで、スムーズな処理が実現します。
PostScript形式で複数ページを保存したい
1#include <TCanvas.h>
2#include <TH1D.h>
3
4TString filename = "output.ps";
5TCanvas *c = new TCanvas("c", "PostScript Output", 800, 600);
6
7// PostScript形式で開始
8c->Print(filename + "[", "ps");
9
10// 複数のページを追加
11for (Int_t i = 0; i < 3; i++) {
12 TH1D *h = new TH1D(Form("h%d", i), Form("Page %d", i), 100, 0, 10);
13 h->FillRandom("gaus", 1000);
14 h->Draw();
15 c->Print(filename, "ps");
16}
17
18// PostScript形式で終了
19c->Print(filename + "]", "ps");
PDFと同様に、PostScript形式でも複数ページの出力がサポートされています。
トラブルシューティング
PDFが開けない、または破損している場合
1// 最初と最後の記号が正確に対応していることを確認
2c->Print("output.pdf" + "[", "pdf"); // OK: 開始
3// ... 処理 ...
4c->Print("output.pdf" + "]", "pdf"); // OK: 終了
5
6// ❌ 間違い: 記号が逆
7// c->Print("output.pdf" + "]", "pdf");
8// c->Print("output.pdf" + "[", "pdf");
複数のファイルに分割したい場合
1// 複数のPDFファイルを作成する場合
2for (Int_t file = 0; file < 3; file++) {
3 TString filename;
4 filename.Form("output_%d.pdf", file);
5
6 TCanvas *c = new TCanvas(Form("c%d", file), "", 800, 600);
7 c->Print(filename + "[", "pdf");
8
9 for (Int_t page = 0; page < 10; page++) {
10 TH1D *h = new TH1D(Form("h%d", page), "", 100, 0, 10);
11 h->FillRandom("gaus", 1000);
12 h->Draw();
13 c->Print(filename, "pdf");
14 }
15
16 c->Print(filename + "]", "pdf");
17}