0
我是C#的新手,我正在使用Linq在c#中的數據表中執行一些操作。我的方法需要大約35秒才能完成處理。有人可以建議如何提高性能?C#代碼需要更多時間來執行
該方法的輸入數據表有35個關鍵績效指標,每個會計年度和每個國家的每個關鍵績效指標都有13個月的數據。因此,dt每個財政年度將有35 * 13 = 455條記錄。無論如何,會有2個會計年度。所以每個國家455 * 2 = 900條記錄。因此,我們正在採取有關的記錄數在輸入數據表
void NeedtoImprovePerformance(DataTable dt)
{
DataView dv = dt.DefaultView;
dv.Sort = "Fiscal_Year ASC";
dt = dv.ToTable();
var kpilist = from table in dt.AsEnumerable()
orderby table.Field<int>("Sub_Service_Type_Id")
group table by new { kpiName = table["KpiName"] } into groupby
select new
{
value = groupby.Key,
columnvalues = groupby
};
var uniqueCountry = from table in dt.AsEnumerable()
group table by new { country = table["CountryName"] } into groupby
select new
{
value = groupby.Key,
columnValues = groupby
};
foreach (var kpi in kpilist)
{
var KpiValues = from table in dt.AsEnumerable()
where table.Field<string>("KpiName") == kpi.value.kpiName.ToString()
select table;
foreach (var countryName in uniqueCountry)
{
var availablePeriods = from table in dt.AsEnumerable()
where table.Field<string>("KpiName").ToString() == kpi.value.kpiName.ToString() &&
table.Field<string>("CountryName").ToString() == countryName.value.country.ToString()
select table.Field<int>("Period").ToString();
if (availablePeriods.Count() < 13 && availablePeriods.Count() > 0)
{
for (int period = 5; period < 17; period++)
{
DataRow dr = dt.NewRow();
if (!availablePeriods.ToList().Contains(period.ToString()))
{
dr[1] = KpiValues.ToList()[0]["KpiName"].ToString();
dr[2] = countryName.value.country.ToString();
dr[3] = (period).ToString();
var availableFiscalYear = from table in dt.AsEnumerable()
where table.Field<int>("Period").ToString() == period.ToString()
select table.Field<string>("Fiscal_Year").ToString();
if (availableFiscalYear == null || availableFiscalYear.Count() == 0)
{
if (ddlFiscalYear.SelectedItem.Text == ddlFiscalYear.Items[ddlFiscalYear.Items.Count - 1].Text)
{
if (period > 10)
dr[4] = ddlFiscalYear.SelectedValue.ToString();
else
dr[4] = (Convert.ToInt32(ddlFiscalYear.SelectedValue) - 1).ToString();
if (period == Convert.ToInt32(ddlMonth.SelectedValue) || period < Convert.ToInt32(ddlMonth.SelectedValue))
dr[4] = (Convert.ToInt32(ddlFiscalYear.SelectedValue) + 1).ToString();
}
else
{
if (period > Convert.ToInt32(ddlMonth.SelectedValue))
dr[4] = (Convert.ToInt32(ddlFiscalYear.SelectedValue) - 1).ToString();
else
{
if (period == Convert.ToInt32(ddlMonth.SelectedValue))
dr[4] = (Convert.ToInt32(ddlFiscalYear.SelectedValue) + 1).ToString();
else
dr[4] = ddlFiscalYear.SelectedValue.ToString();
}
}
}
else
{
dr[4] = availableFiscalYear.ToList()[0].ToString();
}
dr[5] = "";
dr[6] = KpiValues.ToList()[0]["Frequency"].ToString();
dr[7] = KpiValues.ToList()[0]["Sub_Service_Type_Id"].ToString();
dr[8] = KpiValues.ToList()[0]["Service_Type_Id"].ToString();
dr[9] = KpiValues.ToList()[0]["ServiceName"].ToString();
dr[10] = KpiValues.ToList()[0]["OrderBy"];
dt.Rows.Add(dr);
}
if (ddlMonth.SelectedValue == period.ToString())
{
var selectedPeriod = availablePeriods.Where(k => k == ddlMonth.SelectedValue).ToList();
if (selectedPeriod != null && selectedPeriod.Count == 1)
{
var PeriodFiscalYear = from table in dt.AsEnumerable()
where table.Field<string>("KpiName").ToString() == kpi.value.kpiName.ToString() &&
table.Field<string>("CountryName").ToString() == countryName.value.country.ToString()
&& table.Field<int>("Period") == period
select table.Field<string>("Fiscal_Year");
dr = null;
dr = dt.NewRow();
dr[1] = KpiValues.ToList()[0]["KpiName"].ToString();
dr[2] = countryName.value.country.ToString();
dr[3] = (period).ToString();
var availableFiscalYear = from table in dt.AsEnumerable()
where table.Field<int>("Period").ToString() == period.ToString() &&
table.Field<string>("Fiscal_Year").ToString() != PeriodFiscalYear.ToList()[0]
select table.Field<string>("Fiscal_Year").ToString();
if (availableFiscalYear == null || availableFiscalYear.Count() == 0)
{
if (ddlFiscalYear.SelectedItem.Text == ddlFiscalYear.Items[ddlFiscalYear.Items.Count - 1].Text)
{
if (period > 10)
dr[4] = ddlFiscalYear.SelectedValue.ToString();
else
dr[4] = (Convert.ToInt32(ddlFiscalYear.SelectedValue) - 1).ToString();
if (period == Convert.ToInt32(ddlMonth.SelectedValue) || period < Convert.ToInt32(ddlMonth.SelectedValue))
dr[4] = (Convert.ToInt32(ddlFiscalYear.SelectedValue) + 1).ToString();
}
else
{
if (period > Convert.ToInt32(ddlMonth.SelectedValue))
dr[4] = (Convert.ToInt32(ddlFiscalYear.SelectedValue) - 1).ToString();
else
{
if (period == Convert.ToInt32(ddlMonth.SelectedValue))
dr[4] = (Convert.ToInt32(ddlFiscalYear.SelectedValue) + 1).ToString();
else
dr[4] = ddlFiscalYear.SelectedValue.ToString();
}
}
}
else
{
dr[4] = availableFiscalYear.ToList()[0].ToString();
}
dr[5] = "";
dr[6] = KpiValues.ToList()[0]["Frequency"].ToString();
dr[7] = KpiValues.ToList()[0]["Sub_Service_Type_Id"].ToString();
dr[8] = KpiValues.ToList()[0]["Service_Type_Id"].ToString();
dr[9] = KpiValues.ToList()[0]["ServiceName"].ToString();
dr[10] = KpiValues.ToList()[0]["OrderBy"];
dt.Rows.Add(dr);
}
}
}
}
}
}
dv = dt.DefaultView;
dv.Sort = "KpiName ASC, Fiscal_Year ASC, Sub_Service_Type_Id ASC";
dt = dv.ToTable();
}
感謝
在這樣的情況下,只有一件事情要做,那就是使用一個分析器來準確找出吃東西的時間。 –
當你沒有說出瓶頸在哪裏或者它應該做什麼的時候,它有點難...雖然3個嵌套for循環可能不是最好的東西(很難說)(不要介意linq查詢) – Sayse
foreach var countryName in uniqueCountry)對kpilist中的每個kpi花費近1秒。 kpilist擁有大約35個KPI,因此需要大約35秒。 – Kalyan