「ラスティックデータ:Plottersを使用したデータの可視化ー第1部」

Rustic Data Data Visualization with Plotters - Part 1

Rustで生の数値を見事なグラフに変換するための詳細ガイド

Various Plotters Features (Image by author)

要約

Plottersは、データの視覚化を作成するための人気のあるRustライブラリです。さまざまなツールと機能を提供しており、高品質なグラフ、チャート、および他の視覚化を作成するのに役立ちます。この記事は、Plottersで準備された視覚化の美的側面に焦点を当てた一連の記事の第1部です。色のスキームを変更したり、注釈を追加したりすることから、Plottersの視覚化の見た目のカスタマイズ方法を学びます。

この記事を読み終えると、Plottersライブラリを使用して、魅力的な視覚化を作成し、観客を魅了する堅牢な理解を得ることができます。また、データ操作のためのさまざまなツールとメソッドの使用を探求するにあたり、Ndarrayライブラリも役立ちます。したがって、あなたがアマチュアまたは経験豊富なRustプログラマであろうと、Plottersでの情報を提供し、美的に魅力的な視覚化を作成することに興味がある場合は、この記事を読むことが重要です。

注意: この記事では、Rustプログラミング言語の基本的な理解があることを前提としています。

この記事のために開発されたノートブックである6-plotters-tutorial-part-1.ipynbは、以下のリポジトリで見つけることができます:

GitHub – wiseaidev/rust-data-analysis: Rustでの究極のデータ分析コース。

Rustでの究極のデータ分析コース。wiseaidev/rust-data-analysisの開発に貢献して、…を作成します。

github.com

目次(TOC)

∘ 要約; ∘ 目次(TOC) ∘ この記事の対象読者は? ∘ Plottersとは? ∘ Plottersの利点 ∘ Plottersのセットアップ ∘ シングルラインプロット ∘ マルチラインプロット ∘ グリッド、軸、ラベル ∘ 色とマーカー ∘ サブプロット ∘ エラーバー ∘ 散布図 ∘ ヒストグラム ∘ 結論 ∘ 終わりに ∘ リソース

この記事は誰のためのものか

Photo by Myriam Jessier on Unsplash

Rustで直感的なデータの視覚化を作成に興味がある人にとって、この記事は必読です。経験豊富なデータサイエンティストであろうと、初心者であろうと、RustのPlottersクレートを使用することで、観客を感動させる魅力的で目を引くビジュアルを作成することができます。Rustプログラミングの基本的な知識を備えていれば、始めるのはこれまで以上に簡単です。

Plottersクレートは、迅速かつ容易に驚異的で効果的な視覚化を作成する際に非常に強力です。これは個人のプロジェクトだけでなく、プロフェッショナルなプロジェクトにも適しています。複雑な情報を効果的に伝えることができる高品質なグラフィックスを生成するためのツールです。

視覚化スキルをさらに向上させることが魅力的なら、これ以上探す必要はありません! 明解な説明と役立つグラフが、ステップバイステップの指示によって、Plottersクレートを使用して息をのむようなビジュアルを作成するための迅速な進歩を保証します。

Plottersとは何ですか?

Stephen Phillipsによる写真 - Hostreviews.co.uk on Unsplash

Plottersは、柔軟で頑強なRustクレートであり、あなたのような開発者が簡単に見事な視覚化を作成できるように支援します。その多様性により、ライン、スキャッター、ヒストグラムなど、さまざまなプロットの作成が可能であり、スタイリングオプションやカスタマイズされた注釈の高い柔軟性も提供します。

このオールインワンツールにより、開発者は必要な任意のタイプの視覚化を定義できるため、データ分析タスクには欠かせない資産となります。注目すべき機能の1つは、静的なグラフィックの生成だけでなく、Webベースのアプリケーションの作成も可能にする対話型インターフェースのサポートです。この機能により、データセットの簡単な探索が容易になり、機械学習やデータサイエンスのプロジェクトに適したさまざまなプロットタイプを作成できます。

さらに、Plottersは、Jupyter Notebookなどの一般的な開発環境にシームレスに統合され、データ視覚化体験を向上させるために専用の高度なパッケージもサポートしています。これが、このパッケージがどの開発者のツールキットにも欠かせない理由です!

旅の最初のステップを踏み出したばかりであろうと、既に複雑なデータセットを分析している開発者であろうと、Plottersは類いまれな適応性と使いやすさを提供し、今日の最高のツールの一部として認識されるにふさわしいです!

Plottersの利点

UX Indonesiaによる写真

データの視覚化はデータ分析の重要な側面であり、Plottersライブラリはプロセスを簡素化するためのいくつかの利点を提供します。他のオプションとは異なる重要な利点の1つは、使いやすさです。 Ndarrayなどの一般的なデータ分析クレートとの統合により、なじみのある構造とともに簡単に使用できます。

このオープンソースツールを使用することのもう1つの注目すべき利点は、コスト効果の高さです。開発者やアナリストは、使用料や使用権の制限なしにライブラリを利用できます。さらに、ソフトウェアの改善に関心のある人は、コミュニティの取り組みの一環として貢献することができます。

さらに、オープンソースであることは、stackoverflowなどのフォーラムなど、さまざまなプラットフォームを通じて世界中のフェローメンバーからの迅速なオンラインサポートを意味し、問題解決が効率的に行えます!

Plottersのセットアップ

Plottersの機能を最大限に活用するには、環境を正しく設定することが重要です。このライブラリは、ラインチャート、スキャッタープロット、ヒストグラム、パイプロットなど、さまざまなプロットタイプを提供していますが、適切なセットアップがないとこれらの機能にアクセスできません。幸運なことに、Plottersのセットアップは簡単なプロセスです- Jupyter Notebookでコマンドを実行するだけで、準備完了です!

:dep plotters = { version = "^0.3.5", default_features = false, features = ["evcxr", "all_series", "all_elements"] }

プロジェクトのワークスペースまたはノートブックセッションにインポートされた後、Plottersを使用して、必要に応じてシンプルまたは複雑なプロットに特化したさまざまなカスタマイズオプションを探索できます。

シングルラインプロット

線形のシングルラインプロット(著者による画像)

ラインプロットは、データポイントを直線で接続することで表現するための基本的な視覚化ツールです。Plottersライブラリでは、シングルラインプロットの概念を探求します。これには、LineSeries構造体を使用して単一の線で視覚化を作成することが含まれます。

PlottersLineSeries構造体は、特にシングルラインプロットの作成においてデータの可視化に非常に有用です。このようなグラフは、2つの変数間の相関関係を示したり、時系列データ内のパターンを強調するために最適です。

Plottersを使用して一次元プロットを作成するには、ライブラリをインポートし、draw_series関数とLineSeries構造体を使用して、割り当てられたデータセットでラインチャートをスケッチします。たとえば、売上の月次データをシンプルなグラフで示す場合、draw_series関数を次のように使用できます:

evcxr_figure((640, 240), |root| {    let mut chart = ChartBuilder::on(&root)        .build_cartesian_2d(0f32..5f32, 0f32..5f32)?;    let x_axis = [1.0, 2.0, 3.0, 4.0, 5.0, 6.0];    chart.draw_series(LineSeries::new(        x_axis.map(|x| (x, x)),        &RED,    ))?;    Ok(())}).style("width:100%")

上記のコードでは、xとyの両方の座標を表す配列xがあります。次に、シングルラインプロットのデータとしてNdarray配列を使用する別のインスタンスを調べましょう:

evcxr_figure((640, 240), |root| {    let mut chart = ChartBuilder::on(&root)        .build_cartesian_2d(0f32..7f32, 0f32..7f32)?;    let x_axis = Array::range(1., 7., 1.);        chart.draw_series(LineSeries::new(        x_axis.into_raw_vec().into_iter().map(|x| (x, x)),        &RED,    ))?;    Ok(())}).style("width:100%")

次に、方程式y = f(x) = x³で表される2次グラフを可視化しましょう。対応するコードは次の通りです:

let points_coordinates: Vec<(f32, f32)> = {    let x_axis = vec![1.0, 2.0, 3.0, 4.0, 5.0, 6.0];    let quadratic: Vec<f32> = x_axis.iter().map(|x| i32::pow(*x as i32, 3) as f32).collect::<Vec<f32>>();    x_axis.into_iter().zip(quadratic).collect()};points_coordinates// Output// [(1.0, 1.0), (2.0, 8.0), (3.0, 27.0), (4.0, 64.0), (5.0, 125.0), (6.0, 216.0)]

これを次のようにプロットする必要があります:

evcxr_figure((640, 240), |root| {    let mut chart = ChartBuilder::on(&root)        .build_cartesian_2d(0f32..7f32, 0f32..220f32)?;    chart.draw_series(LineSeries::new(        points_coordinates.iter().map(|(x, y)| (*x, *y)),        &RED,    ))?;    Ok(())}).style("width:100%")
A cubic function plot (Image by author)

要約すると、PlottersLineSeriesを使用したラインプロットは、データセット内の相関関係傾向を示すための効果的な手法を提供します。 x値y値の配列/ベクトルを操作しながら、情報を分析するための貴重なツールです。科学的な研究結果の探求やビジネスメトリックの分析など、データセットを掘り下げるための不可欠な手段であり、他の人と情報を効果的に共有するための手段でもあります。

マルチライングラフ

著者によるマルチライングラフ(画像)

プロッターは、単一の出力に複数のグラフを表示する非凡な機能を提供しており、これにより同じ視覚化上で複数の曲線を同時に表示することが可能です。この素晴らしい特性により、データセットの簡単な比較と分析が容易になります。この概念をより深く掘り下げるために、具体的な例を見てみましょう:

evcxr_figure((640, 240), |root| {    let mut chart = ChartBuilder::on(&root)        .build_cartesian_2d(0f32..7f32, 0f32..220f32)?;    chart.draw_series(LineSeries::new(        linear_coordinates.iter().map(|(x, y)| (*x, *y)),        &RED,    ))?;    chart.draw_series(LineSeries::new(        quadratic_coordinates.iter().map(|(x, y)| (*x, *y)),        &GREEN,    ))?;    chart.draw_series(LineSeries::new(        cubic_coordinates.iter().map(|(x, y)| (*x, *y)),        &BLUE,    ))?;    Ok(())}).style("width:100%")

提供されたコードスニペットを利用することで、簡単に多くの曲線を生成することができます。これは、draw_series関数を複数回呼び出し、異なる数学式から得られた対応するy値と組み合わせた配列のx値を定義することによって実現されます。このコードを実行すると、これらのプロットされたすべての曲線を包括的に表示するグラフが観察のために表示されます。

マルチライングラフの適応性を示す別の例について詳しく見てみましょう。次のコードスニペットを確認してください:

let points_coordinates: Vec<(f32, f32)> = {    let x_y_axes = array!([[1., 2., 3., 4.], [1., 2., 3., 4.]]);    let x_axis: Vec<f32> = x_y_axes.slice(s![0, 0, ..]).to_vec();    let y_axis: Vec<f32> = x_y_axes.slice(s![0, 1, ..]).to_vec();    x_axis.into_iter().zip(y_axis).collect()};// [(1.0, 1.0), (2.0, 2.0), (3.0, 3.0), (4.0, 4.0)]evcxr_figure((640, 240), |root| {    let mut chart = ChartBuilder::on(&root)        .build_cartesian_2d(0f32..5f32, 0f32..5f32)?;    chart.draw_series(LineSeries::new(        points_coordinates.iter().map(|(x, y)| (*x, *y)),        &RED,    ))?;    Ok(())}).style("width:100%")

このコードスニペットでは、2つの次元を持つNdarray配列xが異なるデータセットを保持しています。各行は一意の値を示しています。全体の配列にdraw_series関数を呼び出すと、プロッターは複数の曲線として認識し、それらを同時にプロットします。結果は、両方のデータセットが並んで表示され、そのパターン、トレンド、またはその他の注目すべき特徴を直感的に比較・分析するためのものであり、視覚的に意味のある結論を簡単に導き出すことができます。

マルチライングラフの適応性を示すために、任意のデータを使用して視覚的な表現を作成することができます。次のコードスニペットを参考にしてください:

let random_samples: Vec<(f32, f32)> = {    let x_y_axes = Array::random((2, 5), Uniform::new(0., 1.));    let x_axis: Vec<f32> = x_y_axes.slice(s![0, ..]).to_vec();    let y_axis: Vec<f32> = x_y_axes.slice(s![0, ..]).to_vec();    x_axis.into_iter().zip(y_axis).collect()};random_samplesevcxr_figure((640, 240), |root| {    let mut chart = ChartBuilder::on(&root)        .build_cartesian_2d(0f32..1f32, 0f32..1f32)?;    chart.draw_series(LineSeries::new(        random_samples.iter().map(|(x, y)| (*x, *y)),        &RED,    ))?;    Ok(())}).style("width:100%")

このコードスニペットでは、Ndarray関数のArray::randomを使用して、任意の値で埋められた2次元配列を作成しました。このメソッドを使用するたびに、独自のデータポイントのセットが生成されます。生成した配列を出力して、これらのランダムな数値を詳細に調べることができます。draw_series呼び出しは、データセットの各行を個別の曲線として単一のグラフ上に表示します。各実行は異なるランダムな出力を生成するため、生成されるチャートはすべてユニークであり、視覚化の経験に予測不可能性と多様性をもたらします。

まとめると、Plottersを使用して単一の出力で複数のプロットを視覚化する能力は、データの探索と分析において強力な機能です。異なる曲線のプロット、データセットの比較、ランダムデータの活用など、複数の線グラフは手に入る情報の包括的なビューを提供します。Plottersの機能を活用し、さまざまなデータソースで実験することで、理解と意思決定を促進する効果的な視覚化を作成できます。

グリッド、軸、ラベル

Plotters Grid (Image by author)

データの視覚化の世界では、プロット内にグリッドを表示する柔軟性を持つことが重要です。 Plottersライブラリは、メッシュ機能を有効にすることで、これを実現する力を与えてくれます。単にchart.configure_mesh().draw()?;というステートメントをコードに組み込むだけで、プロットの視覚的な魅力と明瞭さを向上させることができます。

evcxr_figure((640, 240), |root| {    let mut chart = ChartBuilder::on(&root)        .build_cartesian_2d(0f32..1f32, 0f32..1f32)?;    chart.configure_mesh().draw()?;    Ok(())}).style("width:100%")

ChartBuilder::on(&root).build_cartesian_2d(0f32..1f32, 0f32..1f32)?;という行では、x軸の範囲を0から1、y軸の範囲を0から1に手動で設定することができます。これにより、プロットされる領域の表示範囲を正確に制御することができ、最も関連性のあるデータポイントが強調されます。

プロットの明瞭さと理解を向上させるために、軸に適切なラベルと記述的なタイトルを提供することが重要です。以下のコードスニペットを例として考えてみましょう:

evcxr_figure((640, 480), |root| {    let mut chart = ChartBuilder::on(&root)        .caption("Plot Demo", ("Arial", 20).into_font())        .x_label_area_size(50)        .y_label_area_size(50)        .build_cartesian_2d(0f32..1f32, 0f32..1f32)?;        chart.configure_mesh()        .x_desc("x = Array::range(1., 7., 0.1);")        .y_desc("y = f(x)")        .draw()?;        Ok(())}).style("width: 60%")
Plotters labels (Image by author)

このコードでは、chart.configure_mesh().x_desc("x = Array::range(1., 7., 1.);").y_desc("y = f(x)").draw()?;というステートメントを追加して、プロットに意味のある注釈を追加しました。 x_desc("x = Array::range(1., 7., 1.);")を含めることで、プロットされるデータの簡潔な説明をx軸にラベル付けします。同様に、y_desc("y = f(x)")は、y軸に関数的な関係を示すラベルを割り当てます。さらに、Caption("Plot Demo", ("Arial", 20).into_font())は、プロットに文脈を与える情報を提供する情報的なタイトルを提供します。これらの要素は、視覚化の解釈可能性を向上させ、視聴者がプロットの目的と内容を簡単に理解できるようにします。

ラベルやタイトルに加えて、プロッターはプロット内の複数の曲線を区別するための凡例を作成することも可能です。 label 関数の引数としてラベルパラメータを渡し、その後 legend 関数を呼び出すことで、凡例を生成することができます。 以下のコード例を参考にしてください:

evcxr_figure((640, 480), |root| {    let mut chart = ChartBuilder::on(&root)        .caption("プロットデモ", ("Arial", 20).into_font())        .x_label_area_size(50)        .y_label_area_size(50)        .build_cartesian_2d(1f32..7f32, 1f32..14f32)?;        let x = Array::range(1., 7., 0.1);        chart.configure_mesh()        .x_desc("x = Array::range(1., 7., 1.);")        .y_desc("y = f(x)")        .draw()?;    chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, *x)),        &RED    )).unwrap()        .label("y = x")        .legend(|(x,y)| PathElement::new(vec![(x,y), (x + 20,y)], &RED));        chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, *x * 2.0)),        &GREEN    )).unwrap()        .label("y = 2 * x")        .legend(|(x,y)| PathElement::new(vec![(x,y), (x + 20,y)], &GREEN));    chart.configure_series_labels()        .background_style(&WHITE)        .border_style(&BLACK)        .draw()?;    Ok(())}).style("width: 60%")
著者による複数行のプロット、ラベル、凡例、およびグリッド付きのプロット(画像)

このコードを実行することで、プロット内のさまざまな曲線に対応する凡例を作成します。 legend() 関数は、draw_series() 関数の呼び出し後に提供されるラベルに基づいて自動的に凡例を生成します。 これにより、視聴者はプロットされている異なる関数を識別し、区別することができます。 グリッド、軸ラベル、およびタイトルと組み合わせて、凡例はプロットの全体的な読みやすさと理解を向上させます。

デフォルトでは、凡例ボックスはプロットの中央右側に配置されます。 ただし、凡例ボックスの場所を変更する場合は、position 関数内の SeriesLabelPosition 位置パラメータを指定することで変更できます。 以下のようにコードスニペットを修正しましょう:

evcxr_figure((640, 480), |root| {    let mut chart = ChartBuilder::on(&root)        .caption("プロットデモ", ("Arial", 20).into_font())        .x_label_area_size(50)        .y_label_area_size(50)        .build_cartesian_2d(1f32..7f32, 1f32..14f32)?;        let x = Array::range(1., 7., 0.1);        chart.configure_mesh()        .x_desc("x = Array::range(1., 7., 0.1);")        .y_desc("y = f(x)")        .draw()?;    chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, *x)),        &RED    )).unwrap()        .label("y = x")        .legend(|(x,y)| PathElement::new(vec![(x,y), (x + 20,y)], &RED));        chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, *x * 2.0)),        &GREEN    )).unwrap()        .label("y = 2 * x")        .legend(|(x,y)| PathElement::new(vec![(x,y), (x + 20,y)], &GREEN));    chart.configure_series_labels()        .position(SeriesLabelPosition::UpperMiddle)        .background_style(&WHITE)        .border_style(&BLACK)        .draw()?;    Ok(())}).style("width: 60%")
著者による図中央上部に配置された凡例を持つ複数行のプロット(画像)

configure_series_labels関数にposition(SeriesLabelPosition::UpperMiddle)パラメータを含めることで、凡例ボックスをプロットの上中央に再配置します。これにより、凡例がプロットされた曲線や他の注釈と干渉しないように、凡例の配置を微調整することができます。凡例の位置をカスタマイズする能力は、プロットの多様性と美観を高めます。

Plottersでこれらの機能を理解し利用することで、視覚的に魅力的で情報量の多いプロットを作成し、軸の範囲をカスタマイズし、ラベルやタイトルを追加し、凡例を組み込み、可視化を画像ファイルとして保存することができます。これらの機能により、データを魅力的かつ意味のある方法で効果的に伝えることができます。

色とマーカー

Plottersは、理解しやすい視覚的に魅力的なプロットをデザインするためのさまざまなスタイルとマーカーを提供しています。スタイルを使用すると、線の外観を変更することができます。マーカーは、プロット上で特定のデータポイントを強調するのに役立ちます。異なる色、スタイル、マーカーをPlottersの機能と組み合わせることで、要件に合わせた独自のプロットを作成することができます。

Plottersは、複雑なデータをカラースペクトルで視覚化するための高度なカラーマップを提供しています。Plottersstyleパラメータを使用すると、事前定義されたカラーマップの配列から選択するか、RGBColorのような組み込みの構造体を使用して独自のカラーマップを設計することができます。このパラメータは、広範な値の範囲を含むデータを表現したり、特定のプロットラインや他の形状を強調したりする際に特に有効です。完全なパレットでは、異なるRGBカラー値を参照できます。

evcxr_figure((640, 480), |root| {    let mut chart = ChartBuilder::on(&root)        .caption("プロットデモ", ("Arial", 20).into_font())        .x_label_area_size(50)        .y_label_area_size(50)        .build_cartesian_2d(1f32..7f32, 1f32..14f32)?;        let x = Array::range(1., 7., 0.1);        chart.configure_mesh()        .x_desc("x = Array::range(1., 7., 0.1);")        .y_desc("y = f(x)")        .draw()?;    chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, *x)),        &RGBColor(0,0,255) // 赤: 0, 緑: 0, 青: 255 -> 青色のプロット     ))?;        Ok(())}).style("width: 60%")
著者による青色の単一行プロット(画像)

この例では、線の色を青に変更しました。また、HSLColorなどの他のカラーフォーマットを使用して、HSLスペクトラム値を指定してカスタムカラーを指定することもできます。

Plottersで線プロットの視覚的な魅力を高めるために、各プロットに異なるシンボルを表すマーカーを組み込むことを検討してください。個人の好みや特定のデータセットの特性に基づいて、サイズや色などのマーカースタイルを使用して、データを2回プロットするdraw_seriesメソッドを活用することができます。

evcxr_figure((640, 480), |root| {    let mut chart = ChartBuilder::on(&root)        .caption("プロットデモ", ("Arial", 20).into_font())        .x_label_area_size(50)        .y_label_area_size(50)        .build_cartesian_2d(1f32..7f32, 1f32..8f32)?;        let x = Array::range(1., 7., 0.1);        chart.configure_mesh()        .x_desc("x = Array::range(1., 7., 0.1);")        .y_desc("y = f(x)")        .draw()?;    chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, *x)),        &RED    ))?;    chart.draw_series(x.map(|x| {        EmptyElement::at((*x, *x))        + Cross::new((0, 0), 2, GREEN) // EmptyElementに対する相対座標    }))?;    Ok(())}).style("width: 60%")
著者によるマーカー付きの線形単一ラインプロット(画像)

または、point_sizeメソッドを使用してマーカーサイズを設定することもできます。これにより、塗りつぶしまたは空の円のマーカーを作成することができます。

evcxr_figure((640, 480), |root| {    let mut chart = ChartBuilder::on(&root)        .caption("プロットデモ", ("Arial", 20).into_font())        .x_label_area_size(50)        .y_label_area_size(50)        .build_cartesian_2d(1f32..7f32, 1f32..8f32)?;        let x = Array::range(1., 7., 0.1);        chart.configure_mesh()        .x_desc("x = Array::range(1., 7., 0.1);")        .y_desc("y = f(x)")        .draw()?;    chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, *x)),        &RED    ).point_size(2))?; // 空の円のマーカー    Ok(())}).style("width: 60%")
著者によるマーカー付きのラインプロット(画像)

これらのテクニック(例:色、マーカー、凡例)を組み合わせて、次のように視覚化をカスタマイズすることができます:

evcxr_figure((640, 480), |root| {    let mut chart = ChartBuilder::on(&root)        .caption("プロットデモ", ("Arial", 20).into_font())        .x_label_area_size(50)        .y_label_area_size(50)        .build_cartesian_2d(1f32..7f32, 1f32..342f32)?;        let x = Array::range(1., 7., 0.1);        chart.configure_mesh()        .x_desc("x = Array::range(1., 7., 0.1);")        .y_desc("y = f(x)")        .draw()?;    chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, *x)),        RED.filled()    ).point_size(2)).unwrap()        .label("y = x")        .legend(|(x,y)| PathElement::new(vec![(x,y), (x + 20,y)], &RED));    chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, (*x).powi(3))),        BLUE    ).point_size(2)).unwrap()        .label("y = x ^ 3")        .legend(|(x,y)| PathElement::new(vec![(x,y), (x + 20,y)], &BLUE));    chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, (*x).powi(2))),        &GREEN    )).unwrap()        .label("y = x ^ 2")        .legend(|(x,y)| PathElement::new(vec![(x,y), (x + 20,y)], &GREEN));    chart.draw_series(x.map(|x| {        EmptyElement::at((*x, (*x).powi(2)))        + Cross::new((0, 0), 2, WHITE) // EmptyElementに対する相対座標    }))?;    chart.configure_series_labels()        .background_style(&WHITE)        .border_style(&BLACK)        .draw()?;    Ok(())}).style("width: 60%")
複数行のプロットで異なるラインの色、マーカー、ラベル、タイトル、凡例(画像)

全体的に、Plottersは色やマーカーを自由にカスタマイズする簡単で効果的な方法を提供し、優れた視覚化を作成することができます。適切なカラーパレットを選ぶことで、プロットは簡単に貴重な情報を伝えることができます。適切な色とマーカーを選ぶことは、メッセージを成功裏に伝えるための重要な要素です。

サブプロット

Plottersサブプロット(著者による画像)

サブプロットの技法は、同じ出力に複数のグラフを表示する強力な方法です。この方法は、異なるデータセットを比較したり、1つのデータセットのさまざまな側面を示したりする場合に特に有用です。 Plottersを使用すると、各プロットの位置を前のプロットに対して相対的に指定できるグリッドレイアウトを作成することができるため、サブプロットの作成は簡単な作業となります。

さらに、各サブプロットにはタイトルやラベルなどのカスタマイズ可能な仕様があり、ユーザーは特定のニーズに応じて出力を調整することが容易です。サブプロットは、科学的およびデータ分析のコンテキストで複雑な情報を扱う際に特に便利であり、重要な発見を簡潔かつ効果的に伝えるのに役立ちます。

Plottersでサブプロットを生成するには、split_evenlyメソッドを使用します。このメソッドは、行数と列数からなるタプルを引数として受け取ります。たとえば、データを最初のプロットにプロットしながら1×2のレイアウトを作成したい場合、次のコードスニペットを使用します:

let linear_coordinates: Vec<(f32, f32)> = {    let x_y_axes = array!([[1., 2., 3., 4.], [1., 2., 3., 4.]]);    let x_axis: Vec<f32> = x_y_axes.slice(s![0, 0, ..]).to_vec();    let y_axis: Vec<f32> = x_y_axes.slice(s![0, 1, ..]).to_vec();    x_axis.into_iter().zip(y_axis).collect()};let quadratic_coordinates: Vec<(f32, f32)> = {    let x_y_axes = array!([[1., 2., 3., 4.], [1., 4., 9., 16.]]);    let x_axis: Vec<f32> = x_y_axes.slice(s![0, 0, ..]).to_vec();    let y_axis: Vec<f32> = x_y_axes.slice(s![0, 1, ..]).to_vec();    x_axis.into_iter().zip(y_axis).collect()};evcxr_figure((640, 480), |root| {    let sub_areas = root.split_evenly((1,2)); // 1行2列のグリッド    let graphs = vec![        ("y = x", linear_coordinates.clone(), &RED),        ("y= x ^ 2", quadratic_coordinates.clone(), &GREEN),    ];    for ((idx, area), graph) in (1..).zip(sub_areas.iter()).zip(graphs.iter()) {        let mut chart = ChartBuilder::on(&area)            .caption(graph.0, ("Arial", 15).into_font())            .x_label_area_size(40)            .y_label_area_size(40)            .build_cartesian_2d(0f32..5f32, 0f32..17f32)?;        chart.draw_series(LineSeries::new(            graph.1.iter().map(|(x, y)| (*x, *y)),            graph.2,        )).unwrap()            .label(graph.0)            .legend(|(x,y)| PathElement::new(vec![(x,y), (x + 20,y)], &GREEN));        chart.configure_mesh()            .y_labels(10)            .light_line_style(&TRANSPARENT)            .disable_x_mesh()            .x_desc("x = Array::range(1., 7., 0.1);")            .y_desc(graph.0)            .draw()?;    }    Ok(())}).style("width:100%")

これにより、サブプロットの1×2のグリッドが作成され、両方のサブプロットにデータがプロットされ、タイトルと軸ラベルが指定されます。 split_evenlyに渡されるタプル引数は、グリッド(1行2列)を表します。 Plottersでは、split_verticallysplit_horizontallysplit_evenlysplit_by_breakpointsを使用してサブプロットを行う方法があります。

Plottersのサブプロット機能を利用することで、洗練された視覚化が可能になります。これにより、洞察を明確かつ正確に提示することでコミュニケーションを支援します。

エラーバー

著者による垂直エラーバーを持つ単一のプロット(画像)

データを正確に表現するためには、誤差の可能性を認識し透明にすることが重要です。これは、測定値の変動性を表示し、不確実性レベルを示すグラフィカルな表現であるエラーバーを使用することで実現できます。Plottersは、ErrorBar関数を使用して、x/y座標、color/styleの設定、および関連するエラー値を指定して、これらの重要な視覚化支援を任意のプロットに追加する簡単なソリューションを提供します。以下のコードスニペットを考えてみましょう:

evcxr_figure((640, 480), |root| {    let mut chart = ChartBuilder::on(&root)        .caption("垂直エラーバーのプロット", ("Arial", 20).into_font())        .x_label_area_size(50)        .y_label_area_size(50)        .build_cartesian_2d(1f32..7f32, 1f32..50f32)?;        let x = Array::range(1., 7., 0.1);    chart.configure_mesh()        .x_desc("x = Array::range(1., 7., 0.1);")        .y_desc("y = f(x)")        .draw()?;    chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, (*x as f32).powi(2))),        &GREEN    )).unwrap()        .label("y = x ^ 2")        .legend(|(x,y)| PathElement::new(vec![(x,y), (x + 20,y)], &GREEN));      chart.draw_series(x.map(|x| {        ErrorBar::new_vertical(*x, (*x as f32).powi(2) - 1.5, (*x as f32).powi(2), (*x as f32).powi(2) + 1.4, RED.filled(), 2)    })).unwrap();    chart.configure_series_labels()        .background_style(&WHITE)        .border_style(&BLACK)        .draw()?;    Ok(())}).style("width: 100%")

この例では、一般的により顕著なため、y軸エラーを表示することを選択しました。次の画像は、データの視覚的表現であり、各データポイントの周りには明確なエラーバーがあります。これらのバーは、特定の信頼レベル内におそらく存在する値の範囲を示しています。バーが長いほど、測定の不確実性が大きいことを示します。

ただし、時系列や複数の独立変数を含む実験データなど、両方の軸にエラーデータを表示することが有益な場合があります。このような場合、ErrorBar::new_horizontalメソッドを使用し、x軸エラーの配列を渡すだけで十分です(y軸エラーについても同様に行います)。

evcxr_figure((640, 480), |root| {    let mut chart = ChartBuilder::on(&root)        .caption("水平エラーバーのプロット", ("Arial", 20).into_font())        .x_label_area_size(50)        .y_label_area_size(50)        .build_cartesian_2d(1f32..7f32, 1f32..50f32)?;        let x = Array::range(1., 7., 0.1);    chart.configure_mesh()        .x_desc("x = Array::range(1., 7., 0.1);")        .y_desc("y = f(x)")        .draw()?;    chart.draw_series(LineSeries::new(        x.iter().map(|x| (*x, (*x as f32).powi(2))),        &GREEN    )).unwrap()        .label("y = x ^ 2")        .legend(|(x,y)| PathElement::new(vec![(x,y), (x + 20,y)], &GREEN));      chart.draw_series(x.map(|x| {        ErrorBar::new_horizontal((*x as f32).powi(2), *x - 0.3, *x, *x + 0.3, RED.filled(), 2)    })).unwrap();    chart.configure_series_labels()        .background_style(&WHITE)        .border_style(&BLACK)        .draw()?;    Ok(())}).style("width: 100%")
作者による水平誤差棒を持つ単一プロット

これらの要素を視覚化に取り入れることで、科学者が研究結果を共有したり、ビジネスアナリストが売上データを表示したりする際に、提示された情報に関連する不確実性をより良く理解することができます。したがって、この重要な機能を利用することにより、データセット内のエラーによる混乱を避けつつ、正確な詳細を正確に伝えることができます。

散布図

散布図はデータを視覚化し、2つの変数関係を理解するための重要なツールです。Rustでは、変数をx軸に割り当て、もう一つをy軸に割り当て、各点をそれぞれの座標にプロットすることで、散布図を簡単に作成することができます。点の色やサイズを操作することで、データセット内の追加の次元を表現することができます。

散布図を使用する主な利点は、表やグラフだけでは明らかにならないデータのパターンクラスターを明確に示すことができる点です。外れ値もこの方法で簡単に特定することができます。

さらに、これらのグラフは直感的な性質を持っており、統計的な専門知識に関係なく、さまざまな要素間の関係を素早く理解することができるため、発見を提示する際に有用なコミュニケーションツールとなります。

次のコードスニペットは、一様分布のデータサンプルの散布図を生成します。

evcxr_figure((640, 480), |root| {    _ = root.fill(&WHITE);    let mut chart = ChartBuilder::on(&root)        .caption("Uniform Distribution Scatter Plot", ("Arial", 20).into_font())        .x_label_area_size(40)        .y_label_area_size(40)        .build_cartesian_2d(0f32..1f32, 0f32..1f32)?;    chart.configure_mesh()        .disable_x_mesh()        .disable_y_mesh()        .y_labels(5)        .x_label_formatter(&|x| format!("{:.1}", *x as f64 / 100.0))        .y_label_formatter(&|y| format!("{}%", (*y * 100.0) as u32))        .draw()?;    let _ = chart.draw_series(random_samples.iter().map(|(x,y)| Circle::new((*x,*y), 3, GREEN.filled())));        Ok(())}).style("width:100%")

生成された散布図は以下の通りです:

作者による一様分布データサンプルの散布図

散布図は、データセットを理解しやすくする強力な視覚化機能を提供し、Rustプログラミング言語環境内で提供されるPlottersのライブラリ関数による簡単な使用方法によって、情報の共有においても直感的な方法を提供してくれます。

ヒストグラム

ヒストグラムは、データの分布を分析する際に非常に有用です。異なるカテゴリやビンに情報がどのように分散しているかを視覚的に表現し、複雑なデータセットを理解し解釈することを容易にします。 Plottersは、線形配列を使用してデータポイントをバーにグループ化することで、このプロセスを簡素化します。

たとえば、ランダムに生成された一様分布をプロットする必要がある場合、ヒストグラムはデータセット内の各可能な結果の頻度を詳細に表示し、データセット内に存在するパターンやトレンドを明らかにします。これらのグラフを分析することで、人口の年齢グループの人口統計、写真でキャプチャされた光の露出レベル、または都市全体で観測される月間降水量など、基礎となる分布について貴重な洞察を得ることができます。

次のコードスニペットは、ランダムに生成された一様分布のデータサンプルをプロットする例です:

evcxr_figure((640, 480), |root| {    let mut chart = ChartBuilder::on(&root)        .caption("ヒストグラム", ("Arial", 20).into_font())        .x_label_area_size(50)        .y_label_area_size(50)        .build_cartesian_2d(0u32..100u32, 0f64..0.5f64)?;    chart.configure_mesh()        .disable_x_mesh()        .disable_y_mesh()        .y_labels(5)        .x_label_formatter(&|x| format!("{:.1}", *x as f64 / 100.0))        .y_label_formatter(&|y| format!("{}%", (*y * 100.0) as u32))        .draw()?;    let hist = Histogram::vertical(&chart)        .style(RED.filled())        .margin(0)        .data(random_samples.iter().map(|(x,_)| ((x*100.0) as u32, 0.01)));    let _ = chart.draw_series(hist);        Ok(())}).style("width:100%")

生成されたヒストグラムは以下の通りです:

作者による一様分布データサンプルのヒストグラムプロット

要約すると、ヒストグラムはさまざまなデータセットの洞察力を高め、時間とともにそれらに影響を与える重要な要素を正確に特定するための強力なツールを提供します。 Plottersの機能を使用することで、私たちのニーズに合わせたカスタマイズ可能なビンサイズなどの特徴を使用することで、大量の情報を正確さを損なわずに迅速に解釈する際の柔軟性が向上します!

結論

Aaron Burden氏による写真

この記事では、視覚化の重要性と、さまざまなニーズに合わせてカスタマイズできるPlottersについて強調しました。 Plottersは、単一行または複数行のグラフ、散布図、ヒストグラムなど、さまざまなタイプのプロットを作成する際に貴重なものでした。さらに、レイアウトデザインの選択肢、カラーライン、マーカー、凡例などのカスタマイズ機能についても学びました。

手に入れた知識を活用することで、Plottersのさまざまな機能を自信を持って活用することができます。これらの方法を効果的に活用することで、データの理解が深まり、結果のより良い伝達が可能になります。

次回のシリーズの記事では、特に第2部では、パイチャートや3Dの視覚化など、魅力的なデータの視覚化について探求します。目標は、あなたがデータのスキルを持つビジュアルストーリーテラーになることであり、これまでにないような隠れた洞察を明らかにすることです!

まとめ

Nick Morrison氏による写真

このチュートリアルを締めくくるにあたり、私は時間とエネルギーを捧げて取り組んでくれたすべての方々に心から感謝を表明したいと思います。Rustプログラミング言語の非凡な能力を一緒に実証することは、まさに喜びでした。

データサイエンスに情熱を持っている私は、今後は関連するトピックについて毎週少なくとも1つの包括的な記事を執筆することを約束します。私の作業に興味を持って最新情報を得るには、さまざまなソーシャルメディアプラットフォームで私とつながるか、直接お問い合わせください。

ありがとうございました!

参考資料

GitHub – wiseaidev/rust-data-analysis: Rust言語による究極のデータ解析コース。

Rust言語による究極のデータ解析コース。wiseaidev/rust-data-analysisの開発に貢献して、…

github.com

plotters – Rust

Plotters – データプロットに焦点を当てたRustの描画ライブラリ、WASMとネイティブアプリケーションの両方に対応しています 🦀📈🚀

docs.rs

evcxr-jupyter-integration

evcxr-jupyter-integration – evcxrはSVGイメージのみを使用し、あらゆる種類のシリーズをサポートしているため、他の種類のバックエンドは必要ありません。そのため、以下を追加する必要があります…

plotters-rs.github.io

We will continue to update VoAGI; if you have any questions or suggestions, please contact us!

Share:

Was this article helpful?

93 out of 132 found this helpful

Discover more