DOBON.NETプログラミング道掲示板
(現在 過去ログ2 を表示中)

[ 最新記事及び返信フォームをトピックトップへ ]

■33768 / inTopicNo.1)  DataGridView内での集計行追加を行いたい
  
□投稿者/ タロウ 一般人(1回)-(2018/01/08(Mon) 12:58:07)
  • アイコン環境/言語:[VB.NET] 
    分類:[.NET] 

    質問失礼します。
    DataGridViewにLinqのクエリ結果をDataSourceとして表示しているものがあるのですが、それに対して、項目ごとの小計行を挿入し、最終行には総合計を表示したいと考えています。

    DataGridViewに対してループ処理で行を追加しようとすると、バインドされているのでプログラムから行追加を行えない、というエラーが帰ります。

    以下の様な表を
    aaa,bbb,10
    aaa,bbb,20
    bbb,aaa,10
    bbb,aaa,20

    を以下の様にしたいです。
    aaa,bbb,10
    aaa,bbb,20
    aaaの小計,,30
    bbb,aaa,10
    bbb,aaa,20
    bbbの小計,,30
    総合計,60

    以上よろしくお願いいたします。
引用返信 削除キー/
■33770 / inTopicNo.2)  Re[1]: DataGridView内での集計行追加を行いたい
□投稿者/ 魔界の仮面弁士 大御所(1096回)-(2018/01/09(Tue) 11:09:24)
  • アイコンNo33768に返信(タロウさんの記事)
    > DataGridViewにLinqのクエリ結果をDataSourceとして表示しているものがあるのですが、それに対して、項目ごとの小計行を挿入し、最終行には総合計を表示したいと考えています。

    デーバインド時に行挿入する場合は、DataSource 側を加工するように
    してみてください。(Linq 側で小計行を作成するようにするということ)
    Linq にするのが難しい場合は、ToList してから加工して
    それを再バインドする形でも良いかと思います。

    もしも編集可能な表としている場合には、小計行を ReadOnly にしたり、
    明細行の編集後に小計行が再集計されるようにするといった作業も
    追加で必要になるかもしれません。
引用返信 削除キー/
■33773 / inTopicNo.3)  Re[2]: DataGridView内での集計行追加を行いたい
□投稿者/ タロウ 一般人(3回)-(2018/01/09(Tue) 20:15:40)
  • アイコンNo33770に返信(魔界の仮面弁士さんの記事)
    > ■No33768に返信(タロウさんの記事)
    魔界の仮面弁士さんありがとうございます。

    > デーバインド時に行挿入する場合は、DataSource 側を加工するように
    > してみてください。(Linq 側で小計行を作成するようにするということ)
    Linq側で小計行を作成するという処理が分からないので、今後の為に具体的に教えていただきたいです。

    > Linq にするのが難しい場合は、ToList してから加工して
    > それを再バインドする形でも良いかと思います。
    今回はこちらで実装しました。

    Linqで小計行と総計行を挿入する方法をよろしければ教えて下さい。
引用返信 削除キー/
■33774 / inTopicNo.4)  Re[3]: DataGridView内での集計行追加を行いたい
□投稿者/ 魔界の仮面弁士 大御所(1098回)-(2018/01/10(Wed) 04:44:24)
  • アイコンNo33773に返信(タロウさんの記事)
    >>デーバインド時に行挿入する場合は、DataSource 側を加工するように
    >>してみてください。(Linq 側で小計行を作成するようにするということ)
    > Linq側で小計行を作成するという処理が分からないので、今後の為に具体的に教えていただきたいです。

    LINQ だと煩わしいかと思いますよ。この場合は、

    (1) Group By クエリ または GroupBy メソッドで小計行を生成
    (2) Aggregate クエリ または Sum メソッドで合計値を生成
    (3) 元のデータ集合に 1 と 2 を Concat メソッドで連結
    (4) Order By クエリ または OrderBy メソッドで並び順を調整して完成

    という流れになるかと思うので。

    同種の小計処理が幾度もある場合は、小計・合計行付きで Yield するための
    拡張メソッドを用意するのがスマートかも知れません。
引用返信 削除キー/
■33775 / inTopicNo.5)  Re[4]: DataGridView内での集計行追加を行いたい
□投稿者/ タロウ 一般人(5回)-(2018/01/10(Wed) 06:02:43)
  • アイコン魔界の仮面弁士さんありがとうございました。
    まだまだ勉強中の身なので、なかなかスマートなものは実装出来ませんが、頑張ってみます。
    お世話になりました。

解決み!
引用返信 削除キー/
■33777 / inTopicNo.6)  Re[4]: DataGridView内での集計行追加を行いたい
□投稿者/ 魔界の仮面弁士 大御所(1100回)-(2018/01/10(Wed) 10:37:15)
  • アイコンNo33774に追記(魔界の仮面弁士の記事)
    >> Linq側で小計行を作成するという処理が分からないので、今後の為に具体的に教えていただきたいです。


    小計行、合計行を出力するサンプルを書いてみました。
    ※ VB2017 向けのコードです

    小計行はグルーピングごとに差し込まねばならないので、今回は
    イテレーターを使って For Each の合間に Yield する実装にしてみました。


    ''' <summary>
    ''' List(Of ) に対する小計サンプル
    ''' </summary>
    Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
      Dim source As New List(Of Tuple(Of String, String, Integer))()
      source.Add(Tuple.Create("aaa", "bbb", 10))
      source.Add(Tuple.Create("aaa", "bbb", 20))
      source.Add(Tuple.Create("bbb", "aaa", 10))
      source.Add(Tuple.Create("bbb", "aaa", 20))

      DataGridView1.DataSource = source

      Dim sample =
        Iterator Function()
          For Each subTotal In From g In source Group By g.Item1 Into Sum(g.Item3), Group
            For Each details In subTotal.Group
              Yield details
            Next
            Yield Tuple.Create($"{subTotal.Item1}の小計", "", subTotal.Sum)
          Next
          If source.Any() Then
            Yield Tuple.Create("総合計", "", Aggregate r In source Into Sum(r.Item3))
          End If
        End Function

      DataGridView2.DataSource = sample().ToArray()
    End Sub

    ''' <summary>
    ''' DataTable に対する小計サンプル
    ''' </summary>
    Private Sub Button2_Click(sender As Object, e As EventArgs) Handles Button2.Click
      Dim source As New DataTable()
      source.Columns.Add("Item1", GetType(String))
      source.Columns.Add("Item2", GetType(String))
      source.Columns.Add("Item3", GetType(Integer))

      source.Rows.Add("aaa", "bbb", 10)
      source.Rows.Add("aaa", "bbb", 20)
      source.Rows.Add("bbb", "aaa", 10)
      source.Rows.Add("bbb", "aaa", 20)

      DataGridView1.DataSource = source

      Dim sample =
        Iterator Function()
          For Each subTotal In From g In source Group By Item1 = g.Field(Of String)("Item1") Into Sum(g.Field(Of Integer)("Item3")), Group
            For Each details In subTotal.Group
              Yield details
            Next
            Dim subTotalRow = source.NewRow()
            subTotalRow("Item1") = $"{subTotal.Item1}の小計"
            subTotalRow("Item3") = subTotal.Sum
            Yield subTotalRow
          Next
          If source.Rows.Count > 0 Then
            Dim totalRow = source.NewRow()
            totalRow("Item1") = "総合計"
            totalRow("Item3") = Aggregate r In source Into Sum(r.Field(Of Integer)("Item3"))
            Yield totalRow
          End If
        End Function

      DataGridView2.DataSource = sample().CopyToDataTable()
    End Sub
引用返信 削除キー/
■33778 / inTopicNo.7)  Re[5]: DataGridView内での集計行追加を行いたい
□投稿者/ タロウ 一般人(6回)-(2018/01/10(Wed) 19:27:57)
  • アイコン魔界の仮面弁士様ありがとうございます。
    素晴らしいサンプルを作成していただきありがとうございます。
    今後、躓くことがあったらまた宜しくお願いします。
解決み!
引用返信 削除キー/



トピック内ページ移動 / << 0 >>

このトピックに書きこむ

過去ログには書き込み不可

Mode/  Pass/


- Child Tree -