how i can sum an column in datatable in different dates? - vb.net

i am trying to sum an column in datatable by different dates and displaying the value in textbox but only i am getting the first row value in the column not the the sum , i attached an picture and my code is
Dim dt As DataTable = New DAL().selectdatatable(String.Format("
SELECT
SUM(PT.PT_Paid) AS SumOfPT_Paid
, SUM(PT.PT_Remain) AS SumOfPT_Remain
, PT.PT_Date
FROM
PT
GROUP BY
PT.PT_Date
HAVING
(
(
(
PT.PT_Date
)
>=#{0}#
AND
(
PT.PT_Date
)
<=#{1}#
)
)
;", dateshow.Value.ToString("dd/MM/yyyy"), dateshow2.Value.ToString("dd/MM/yyyy")))
If dt.Rows.Count > 0 Then
txtin.Text = dt.Rows(0)(0).ToString
txtremain.Text = dt.Rows(0)(1).ToString
Else
txtin.Text = "0"
txtremain.Text = "0"
End If
Data:

Related

How to change all the values in the column in datagridview

I want to set the value in the data grid view if the column "is_active" have the value of 0 then it show "ACTIVE" not 0.
MY CODE:
Dim dt As DataTable
dt = exec("select * from tbl_credentials where is_active = 1 and is_status = 2")
If DataGridView1.Columns(3).ToString = 1 Then
dt.Columns(3).value = "ACTIVE"
End If
DataGridView1.DataSource = dt
use select CASE :
Dim dt As DataTable
dt = exec("select username,password, CASE is_active WHEN 0 then 'ACTIVE' ELSE '' END from tbl_credentials")
DataGridView1.DataSource = dt

sql query with multiple headers and multiple counts

I have a table with client task details (attached picture). I want result like number of tasks received for a particular month for each client, no. of tasks completed within 5days from the start date and its compliance. could someone help with a SQL query
client | No.of tasks of a month | No.of tasks completed on time | % of compliance
A | 5 | 4 | 75%
Assuming you have a quite recent sql-server, try something like this (change the name of table and columns as appropriate).
select
x.Client
, x.MonthTasks
, x.CompletedOnTime
, Compliance = x.CompletedOnTime * 100 / x.MonthTasks
from (
select
t.Client
, MonthTasks = Count(1)
, CompletedOnTime = SUM(CASE WHEN DATEDIFF(day, t.TaskStart, t.TaskEnd)<=5 THEN 1 ELSE 0 END)
from tasks as t
where
year(t.TaskStart) = 2018 -- put year
and month(t.TaskStart) = 10 -- put month
group by t.Client
) as x
order by x.Client
About your last comment, this is a minimal, not-production-ready, idea:
suppose you have a combobox for months and year
cbYear.DataSource = new int[] { 2017, 2018, 2019 };
cbMonth.DataSource = new string[] { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Ago", "Sep", "Oct", "Nov", "Dec" };
and a datagridview dgv, you can do something like this (in a button)
SqlConnection con = new SqlConnection("Data Source=(LocalDb)\\MSSQLLocalDB;Initial Catalog=test;Integrated Security=SSPI");
con.Open();
SqlCommand cmd = con.CreateCommand();
cmd.CommandText = #"
select
x.Client
, x.MonthTasks
, x.CompletedOnTime
, Compliance = x.CompletedOnTime * 100 / x.MonthTasks
from (
select
t.Client
, MonthTasks = Count(1)
, CompletedOnTime = SUM(CASE WHEN DATEDIFF(day, t.TaskStart, t.TaskEnd)<=5 THEN 1 ELSE 0 END)
from tasks as t
where
year(t.TaskStart) = #year
and month(t.TaskStart) = #month
group by t.Client
) as x
order by x.Client
";
cmd.Parameters.AddWithValue("#year", cbYear.SelectedItem);
cmd.Parameters.AddWithValue("#month", cbMonth.SelectedIndex +1);
var dr = cmd.ExecuteReader(CommandBehavior.CloseConnection);
var dt = new DataTable();
dt.Load(dr);
dgv.AutoGenerateColumns = true;
dgv.DataSource = dt;
dgv.Refresh();
I repeat you have to catch any errors, maybe transform the query in a stored procedure, but this can be a starting point.

Datatables combine data from different columns into single row

Refer to the below image, how to merge all chapter into one single rows of different page number?
e.g.
Page 1 has 3 rows as there are 3 data at columns of chp 8,9,10
Page 2 has 5 rows as there are 5 data at columns of chp 8,9,1,11,12
So
how to have a single row of each page number and the all data placed at their own chp?
Basic SQL as below:
SELECT `mc_ee_page_id` as Page,
IF ( mc_ee_chp_id = 1, ( CASE
WHEN (is_marked = 0 and mk_no_mark = 1 ) THEN "Y"
WHEN (is_marked = 1 and mk_no_mark = -1) THEN "N"
WHEN (is_marked = 1 and mk_no_mark = 1 ) THEN "O" ELSE "X"
END ) , "" ) AS chp_1 ,
IF ( mc_ee_chp_id = 2, ( CASE
WHEN (is_marked = 0 and mk_no_mark = 1 ) THEN "Y"
WHEN (is_marked = 1 and mk_no_mark = -1) THEN "N"
WHEN (is_marked = 1 and mk_no_mark = 1 ) THEN "O" ELSE "X"
END ) , "" ) AS chp_2 ,
IF ( mc_ee_chp_id = 3, ( CASE
WHEN (is_marked = 0 and mk_no_mark = 1 ) THEN "Y"
WHEN (is_marked = 1 and mk_no_mark = -1) THEN "N"
WHEN (is_marked = 1 and mk_no_mark = 1 ) THEN "O" ELSE "X"
END ) , "" ) AS chp_3 ,
:
:
IF ( mc_ee_chp_id = 12, ( CASE
WHEN (is_marked = 0 and mk_no_mark = 1 ) THEN "Y"
WHEN (is_marked = 1 and mk_no_mark = -1) THEN "N"
WHEN (is_marked = 1 and mk_no_mark = 1 ) THEN "O" ELSE "X"
END ) , "" ) AS chp_12
FROM `maxcare_mc_ee_hw`
WHERE `stud_id` = '3312' AND `mc_ee_level_id` = '1'
GROUP BY mc_ee_chp_id, mc_ee_page_id
ORDER BY mc_ee_page_id asc
LIMIT 500
One way would be to GROUP the results of your SQL by making it the subquery of an outer query...
SELECT Page, MAX(chp_1) AS chp_1, MAX(chp_2) AS chp_2, MAX(chp_3) AS chp_3, MAX(chp_4) AS chp_4, MAX(chp_5) AS chp_5, MAX(chp_6) AS chp_6, MAX(chp_7) AS chp_7, MAX(chp_8) AS chp_8, MAX(chp_9) AS chp_9, MAX(chp_10) AS chp_10, MAX(chp_11) AS chp_11, MAX(chp_12) AS chp_12
FROM
(
-- *** paste your SQL in here ***
) AS indivdual_rows
GROUP BY Page
It assumes a page cannot have more than one non-blank value for the same chapter. If that is not the case, then it will only show the MAX alphabetical value.
Click here to go to SQL Fiddle to see it in action.

how to perform groupby in linq on DataTable inside vb code?

How do I perform group in LINQ inside vb code (dot.net v4.0) with DataTable and sum on the group?
In the sample below I need to add group by GroupName, ProductName and perform sum on QTY. The columns, order and where should remain as in sample, I just need to add the group and sum. The format should remain the same (getting row using e("FieldName")).
Dim ordersTable As DataTable = _dsProd.Tables("tblProductSummary")
Dim query =
(From e In ordersTable
Where (e("Type").ToString() = "1" Or IsDBNull(e("Type")))
Order By e("GroupSortOrder") Ascending, e("ProductName")
Select
GroupName = e("GroupName"),
ProductName = e("ProductName"),
QTY = e("QTY"),
Type= e("Type")
)
Dim query =
(From e In ordersTable
Where (e("Type").ToString() = "1" Or IsDBNull(e("Type")))
Order By e("GroupSortOrder") Ascending, e("ProductName")
Group e By Key = New With {
.ProductName = e("ProductName"),
.GroupName = e("GroupName")
} Into Group
Select New With {
.ProductName = Key.ProductName,
.GroupName = Key.GroupName,
.Sum = Group.Sum(Function(x) x("QTY"))
})

How to handle a division by zero in Linq

In the following linq query I have a division by zero exception wich I can't seem to code around. It occurs when the Sum of fldDevider returns 0.
Dim lstToReturn As List(Of MonthData)
lstToReturn = (
From myRow In dtSpotData.AsEnumerable()
Group myRow By myRow.Field(Of DateTime)(fldstartdate).Month Into Group
Select New MonthData() With {
.Month = Month,
.ValuePerMonth =
(
Group.Sum(Function(dr) dr.Field(Of [Decimal])(fldSomeGeneralValue)) /
(
Group.Sum(Function(dr) CDec(dr.Field(Of String)(fldDevider)))
)
)
}
).ToList()
How can I Make sure the ValuePerMonth field is 0 when the Group.Sum(Function(dr) CDec(dr.Field(Of String)(fldDevider))) function returns a 0. Or how do I return a 1 for Sum fldDevider if it is actually 0.
Some tips on how to do better conversions from string to decimal are welcome too.
I am used to C# syntax but I would use a 'let' to capture the value of the dividing number and only use it if it is greater than zero, and otherwise use 1.
Dim lstToReturn As List(Of MonthData)
lstToReturn = (
From myRow In dtSpotData.AsEnumerable()
Group myRow By myRow.Field(Of DateTime)(fldstartdate).Month Into Group
Let div = Group.Sum(Function(dr) CDec(dr.Field(Of String)(fldDevider)))
Select New MonthData() With {
.Month = Month,
.ValuePerMonth =
(
Group.Sum(Function(dr) dr.Field(Of [Decimal])(fldSomeGeneralValue)) / If(div > 0, div, 1)
)
}
).ToList()