I have this two codes.First one create date from today to seven days before except weekends. How can i combine second code to first one. I need to get dates from first code and use it for compare with m.CreationDate . I will use this code for : get typeid 1 and that days total book number for everydays. Thanks for answer...
public static List<DateTime> GetBusinessDays(DateTime startDate, int numDays)
{
var dates = new List<DateTime>();
var step = (numDays < 0) ? -1 : 1;
var date = startDate;
var absNumDays = Math.Abs(numDays);
while (dates.Count() < absNumDays)
{
date = date.AddDays(step);
if (date.DayOfWeek == DayOfWeek.Saturday || date.DayOfWeek == DayOfWeek.Sunday)
continue;
dates.Add(date);
}
return dates;
}
string DateString = "";
var start = DateTime.Now;
var Dates = GetBusinessDays(start,-7);
Dates.Reverse();
foreach (var date in Dates)
{
DateString = DateString + "'" + date.ToShortDateString() + "',";
}
DateString = DateString.TrimEnd(',');
var book = from m in Connection.Db.Materials
where m.TypeId == 1 && m.25.05.2015,.ToShortDateString() == xx//need to write days here but for everyday
group m by m.TypeId into g
select new { Count = g.Count()};
get data from Dates :18.5.2015, 19.05.2015,20.05.2015,21.05.2015,22.05.2015,25.05.2015,26.05.2015.
I trying to get: m.CreationDate ==
19.05.2015 and typeid ==1 total book numbers:50
m.CreationDate ==
20.05.2015 and typeid ==1 total book numbers:15
If you toss the dates into a collection then you can use Contains in linq
var book = from m in Connection.Db.Materials
where m.TypeId == 1 && CreationDatesArray.Contains(m.CreationDate)
group m by m.TypeId into g
select new { Count = g.Count()};
Added m. as pointed out
Ok. You have date collection in Dates.
Then you perform grouping as
var book = from m in Connection.Db.Materials
where m.TypeId == 1
group m by m.CreationDate into g
select g
Then you can do
var result = Dates.Select(d => new {
Date = d,
Count = book.Where(g => g.Key == d).Count() })
And in result you get collection of dates from Dates with count from your second collection.
string DateString = "";
var start = DateTime.Now;
var Dates = GetBusinessDays(start,-7);
Dates.Reverse();
foreach (var date in Dates)
{
DateString = DateString + "'" + date.ToShortDateString() + "',";
}
DateString = DateString.TrimEnd(',');
var book = from m in Connection.Db.Materials
where m.TypeId == 1
group m by m.CreationDate into g select g;
var results = Dates.Select(d => new { Date = d.Day + "/" + d.Month + "/" + d.Year, Count = book.Where(g => g.Key.Day == d.Day && g.Key.Month == d.Month && g.Key.Year == d.Year).Count() }).ToList();
//put day, month and year. Because only dates equals with ohter dates.(I need only dates not times)
string Books = "";
foreach(var r in results)
{
Books = Books + r.Count + ',';
}
Thanks Everbody for Helping
Related
I need to get data from the current month.Haven't been able to find a solution that works.
This is my code, which gives me the data I need, but I get data from a whole month back, instead of from the current month we are in.
I chose the date "limit" twice with row > DateTime.Today.Addmonths(-1)
Any ideas ?
var userQuery =
from timeEntry in TimeEntries
//this displays a month back, not current month TODO: change to current month.
where timeEntry.DateEntity > DateTime.Today.AddMonths(-1)
select new {
UserName = timeEntry.User.FirstName + " " +timeEntry.User.LastName,
HoursEntered = timeEntry.HoursEntered,
User = timeEntry.User
};
var localrows = userQuery.ToList();
var grouping = localrows.GroupBy(x => x.User);
var userList = grouping.Select(q => new {
UserName = q.FirstOrDefault().UserName,
Hours = q.Sum(hr => hr.HoursEntered), //AbsenceTypeID = holiday(1) // still takes from a whole month, instead of current month.
Holiday = q.FirstOrDefault().User.Absences.Where(a => a.AbsenceTypeID == 1).Where(date => date.DateEntity > DateTime.Today.AddMonths(-1)).Count(),
});
EDIT:
Keyur patel' answer worked, though not for the bottom one.
so there i have to thank Jules for this one:
DateTime.Today.AddDays((DateTime.Today.Day -1) * -1)
Try using this:
DateTime today = DateTime.Today;
var userQuery =
from timeEntry in TimeEntries
where timeEntry.DateEntity.Month == today.Month && timeEntry.DateEntity.Year == today.Year
select new {
UserName = timeEntry.User.FirstName + " " +timeEntry.User.LastName,
HoursEntered = timeEntry.HoursEntered,
User = timeEntry.User
};
Added check for .Year since it may match with months from other years, if you have any.
Edit
As for the holiday part:
var userList = grouping.Select(q => new {
UserName = q.FirstOrDefault().UserName,
Hours = q.Sum(hr => hr.HoursEntered),
Holiday = q.FirstOrDefault().User.Absences.Where(a => a.AbsenceTypeID == 1 && a.DateEntity.Month == today.Month && a.DateEntity.Year == today.Year).Count(),
});
You can simply compare only Month part of the date like this:
timeEntry.DateEntity.Month == DateTime.Now.Month
You can use Month and Year properties of the DateTime class as follows:
var userQuery = TimeEntries
.Where (te => te.DateEntity.Month == DateTime.Today.Month && te.DateEntity.Year == DateTime.Today.Year)
.Select(timeEntry =>
new {
UserName = timeEntry.User.FirstName + " " + timeEntry.User.LastName,
HoursEntered = timeEntry.HoursEntered,
User = timeEntry.User
}
);
You can try this:
.Where(x => x.EntityDate >= new DateTime(DateTime.Now.Year, DateTime.Now.Month, 1));
can u help me to solve this.
i'm retrieving the balance of each heads, and i retrieved the balance of each heads. Now i want to list the balance in the descending order and list the name instead of h_id. i used the code
protected void account_watchlist() {
using(var context = new sem_dbEntities()) {
//ledger && head
var year = DateTime.Now.AddMinutes(318).Year;
var month = DateTime.Now.AddMinutes(318).Month;
var start = new DateTime();
if (month >= 4) {
start = new DateTime(year, 04, 01);
} else if (month < 4) {
start = new DateTime(year - 1, 04, 01);
}
var qr = (from a in context.ledgers
where a.entry_date >= start && a.entry_date < new DateTime(year, month, 1)
join b in context.heads on a.h_id equals b.h_id
group a by a.h_id into sb select new {
sb.FirstOrDefault().h_id,
totalc = sb.Sum(c => c.credit),
totald = sb.Sum(d => d.debit),
balance = sb.Sum(d => d.debit) - sb.Sum(c => c.credit)
}).ToList();
Repeater2.DataSource = qr.ToList();
Repeater2.DataBind();
}
}
You need to use group join of heads with ledgers. It will give you access both to head entity and all related ledgers (in headLedgers collection):
from h in context.heads
join l in context.ledgers.Where(x => x.entry_date >= startDate && x.entry_date < endDate)
on h.h_id equals l.h_id into headLedgers
where headLedgers.Any()
let totalc = headLedgers.Sum(l => l.credit),
let totald = headLedgers.Sum(l => l.debit),
select new {
h.h_id,
h.name,
totalc,
totald,
balance = totald - totalc,
}
I also introduced two range variables for total credit and total debit (consider better names here) to avoid calculating them second time for balance.
using (DataAccessAdapter adapter = new DataAccessAdapter())
{
LinqMetaData meta = new LinqMetaData(adapter);
var datas = (from x in meta.Table
where x.DateCreated >= startDate && x.DateCreated <= endDate && x.ViaTo > 0 && !x.Cancelled
group x by new { month = x.DateCreated.Value.Month } into g
select new
{
MonthNr = g.Key,
//MonthName = ?
TotalMonthAmount = g.Sum(x => x.Amount)
});
.....
}
And startDate & endDate are valid Dates.
I only get the month number, how to get the month name for the DateCreated?
You can get the month name using this function:
CultureInfo.CurrentCulture.DateTimeFormat.GetMonthName(monthNumber);
new { month = x.DateCreated.Value.Month.ToString("MMM") }
I think you are asking about Month property. Check this:
using System;
class Program
{
static void Main()
{
DateTime now = DateTime.Now;
//
// Write the month integer and then the three-letter month.
//
Console.WriteLine(now.Month); //outputs 5
Console.WriteLine(now.ToString("MMM")); //outputs May
}
}
How would I get this query to get the monthly count data for the past 12 months? I don't want to hard code the range, I want to use the current date DateTime.Now and get all the data for the past 12 months from that. I am trying to avoid adding a calendar table to the database and do this just using LINQ.
Some months might not have any data but I still need a count of 0 for those.
For example. If my data contains
Date Count
12/2/2013, 4
10/1/2014, 1
11/5/2014, 6
The results should be, using the current date of 11/9/2014
11/2013, 0
12/1013, 4
1/2014, 0
2/2014, 0
3/2014, 0
4/2014, 0
5/2014, 0
6/2014, 0
7/2014, 0
8/2014, 0
9/2014, 0
10/2014, 1
11/2014, 6
I can't get it to work. I think it's how I'm using Range but I'm not sure.
TimeSpan ts = new TimeSpan(365, 0, 0, 0);
DateTime yearAgo = DateTime.Now.Subtract(ts);
var changesPerYearAndMonth =
from year in Enumerable.Range(yearAgo.Year, 1)
from month in Enumerable.Range(1, 12)
let key = new { Year = year, Month = month }
join revision in list on key
equals new { revision.LocalTimeStamp.Year,
revision.LocalTimeStamp.Month } into g
select new { GroupCriteria = key, Count = g.Count() };
I have modified the answer from this this link as a starting point.
Linq: group by year and month, and manage empty months
I just found this article that is the same question but unanswered
Linq - group by datetime for previous 12 months - include empty months
To get the past twelve months, use
var now = DateTime.Now;
var months = Enumerable.Range(-12, 12)
.Select(x => new {
year = now.AddMonths(x).Year,
month = now.AddMonths(x).Month });
To be safe you should first move 'now' to the start of the month to avoid any end-of-month effects with AddMonth.
var now = DateTime.Now;
now = now.Date.AddDays(1-now.Day);
Complete example:-
var list = new [] {
new { LocalTimeStamp = DateTime.Parse("12/2/2013"), count = 4},
new { LocalTimeStamp = DateTime.Parse("10/1/2014"), count = 1 },
new { LocalTimeStamp = DateTime.Parse("11/5/2014"), count = 6}
};
var now = DateTime.Now;
now = now.Date.AddDays(1-now.Day);
var months = Enumerable.Range(-12, 13)
.Select(x => new {
year = now.AddMonths(x).Year,
month = now.AddMonths(x).Month });
var changesPerYearAndMonth =
months.GroupJoin(list,
m => new {month = m.month, year = m.year},
revision => new { month = revision.LocalTimeStamp.Month,
year = revision.LocalTimeStamp.Year},
(p, g) => new {month = p.month, year = p.year,
count = g.Sum(a => a.count)});
foreach (var change in changesPerYearAndMonth)
{
Console.WriteLine(change.month + " " + change.year +" " + change.count);
}
You don't need a 3-way join, you just need to filter your data before grouping.
1) Query expression syntax
// since your list item type was not posted, anyway same access as your LocalTimeStamp property
list = new List<DateTime>();
DateTime aYearAgo = DateTime.Now.AddYears(-1);
var dateslastYear = from date in list
where date > aYearAgo
group date by new { date.Year, date.Month } into g
select new { GroupCriteria = g.Key, Count = g.Count() };
2) Chained
dateslastYear = list.Where (d=>d>aYearAgo)
.GroupBy (date=>new{date.Year, date.Month });
3) If you want grouping by year/month pairs, including records of not existent entries, and also omitting those pairs that are older than a year occurring with the joined Enumerable.Range call:
var thisYearPairs = from m in Enumerable.Range(1, DateTime.Now.Month)
select new { Year = DateTime.Now.Year, Month = m };
var lastYearPairs = from m in Enumerable.Range(DateTime.Now.Month, 12 - DateTime.Now.Month + 1)
select new { Year = DateTime.Now.Year - 1, Month = m };
var ymOuter = from ym in thisYearPairs.Union(lastYearPairs)
join l in list on new { ym.Year, ym.Month } equals new { l.Year, l.Month } into oj
from p in oj.DefaultIfEmpty()
select new { a = ym, b = p == null ? DateTime.MinValue : p };
var ymGroup = from ym in ymOuter
group ym by ym into g
select new { GroupCriteria = g.Key.a, Count = g.Key.b == DateTime.MinValue ? 0 : g.Count() };
You are taking the range for the 12 months of last year only but you actually want the last twelve months.
You can do this using a Enumerable.Range and the AddMonths method:
var changesPerYearAndMonth =
from month in Enumerable.Range(0, 12)
let key = new { Year = DateTime.Now.AddMonths(-month).Year, Month = DateTime.Now.AddMonths(-month).Month }
join revision in list on key
equals new
{
revision.LocalTimeStamp.Year,
revision.LocalTimeStamp.Month
} into g
select new { GroupCriteria = key, Count = g.Count() };
public int YearDiff(DateTime a, DateTime b)
{
return (int) Math.Floor((a.Year + a.Month / 100.0 + a.Day / 10000.0) - (b.Year + b.Month / 100.0 + b.Day / 10000.0));
}
I have a form which user select start and end date to get data.
Although user select start and end date i have to show data from table week by week in date range.
My model is simple
public class DateBetween
public Datetime StartDate{ get;set;}
public Datetime EndDate{ get;set;}
I get list of my datas between these dates from database
IList<Revenue> datas = DB.CreateCrateria(typeof(Revenue))
.Add(Restrictions.Bt("Date", model.startDate, model.endDate))
.List<Revenue>();
public class Revenue
public int Id{ get;set;}
public double Revenue { get;set;}
public Datetime RevenueDate{ get;set;}
Example:
id Date Revenue
1 10/11/2011 554
2 11/10/2011 500
etc
If user select date like 6/30/2011 and 10/15/2011
I want to show to user
Week Date Avg.Revenue
Week 1 6/30/2011-7/2/2011 587
Week 2 7/3/2011-7/9/2011 650
...
etc
Is there any recommendation doing with aggregate funct. in linq
You could use a handwritten LINQ or use this answer:
LINQ query to split an ordered list into sublists of contiguous points by some criteria
Example: using nothing else than plain Linq and DateTime/Calendar:
var rnd = new Random();
var data = Enumerable.Range(1,100).Select(i => DateTime.Now.AddDays(rnd.Next(-91000,91000)/24));
var calendar = CultureInfo.CurrentCulture.Calendar;
Func<DateTime, int> twoWeeks = dt => (dt.Year * 100) + 2 * (calendar.GetWeekOfYear(dt, CalendarWeekRule.FirstFullWeek, DayOfWeek.Sunday) / 2);
var by2weeks = data.GroupBy(twoWeeks);
foreach (var period in by2weeks.OrderBy(g => g.Key))
{
Console.WriteLine("{0}: {1}", period.Key, string.Join(", ", period));
}
For C# 3.5 and earlier string.Join(", ", period)
string.Join(", ", period.Select(o => o.ToString()).ToArray())
The trick was getting the exact calendar start date for each week in any given year, and for that I looped on DateTime's Office Automation method. Doing that produced a Dictionary with 53 entries. After that, it was all standard LINQ grouping and referencing into the dictionary for the start date.
Calendar cal = Calendar.ReadOnly(CultureInfo.CurrentCulture.Calendar);
StringBuilder sb = new StringBuilder();
DirectoryInfo rdi = new DirectoryInfo(Root); // get all files in the root directory
List<FileInfo> allfis = rdi.GetFiles("*", SearchOption.AllDirectories).ToList();
var a = allfis.GroupBy(q=>cal.GetYear(q.LastWriteTime));
foreach (var b in a.Where(q=>q.Key==2011)) // this year only
{
double yearStartOaDate = new DateTime(b.Key, 1, 1).ToOADate();
double yearEndOaDate = yearStartOaDate + 365;
// get exact start dates for each week
Dictionary<int, DateTime> weekStartingDates = new Dictionary<int, DateTime>();
while (yearStartOaDate <= yearEndOaDate)
{
DateTime dt = DateTime.FromOADate(yearStartOaDate);
int ww = cal.GetWeekOfYear(dt, CalendarWeekRule.FirstDay, DayOfWeek.Sunday);
if(!weekStartingDates.ContainsKey(ww))
{
weekStartingDates.Add(ww, dt);
}
yearStartOaDate += ww == 1 ? 1 : 7;
}
var c = b.GroupBy(q => cal.GetWeekOfYear(q.LastWriteTime, CalendarWeekRule.FirstDay, DayOfWeek.Sunday)).OrderBy(q=>q.Key);
foreach(var d in c)
{
sb.AppendLine("Between " + weekStartingDates[d.Key].ToShortDateString() + " and " + weekStartingDates[d.Key].AddDays(6).ToShortDateString() + " there were " + d.Count() + " files modified");
}
}
File.WriteAllText("results.txt", sb.ToString());
And the results were...
Between 09/01/2011 and 15/01/2011 there were 22 files modified
Between 12/06/2011 and 18/06/2011 there were 11 files modified
etc etc.
First Select date object with WeekOfYear then group on it and ...
var result = datas.Select(p => new
{
week = EntityFunctions.DiffDays(EntityFunctions.CreateDateTime(p.Date.Year, 1, 1, 0, 0, 0), p.Date.Value).Value / 7,
Date= p.Date,
Revenue= p.Revenue
}).GroupBy(p => p.week)
.Select(p => new
{
week=p.Key,
Date=string.Format("{0:M/d/yyyy}",p.Min(q=>q.Date))+"-"+string.Format("{0:M/d/yyyy}",p.Max(q=>q.Date))
Revenue=p.Average(q=>q.Revenue)
}).ToList();