简体   繁体   English

用于访问数据表记录的C#代码优化

[英]C# code optimization for accessing datatable records

i have a cost issue with datatable. 我在数据表方面存在成本问题。 And i need to replace the code with a smarter one. 而且我需要用更智能的代码替换代码。

i have a datatable and the sample values are like this: 我有一个数据表,样本值是这样的:

Columns : id, user_id, starttime, endtime 列:id,user_id,开始时间,结束时间

Row Sample : 1 , 5, 05.10.2009 08:00:00,05.10.2009 17:00 行样本:1,5,05.10.2009 08:00:00,05.10.2009 17:00

my pseudo code is 我的伪代码是

    function something()
    {
    for(int i=0;i<datatable.Rows.Length;i++)
    {
    if(Someobject.variable.Equals(dt.Rows[i][user_id].ToString()))
    {
    if(Date.Compare(somevariable,dt.Rows[i][starttime].ToString())!=0)
    {
    //Do something
    }
    }
    }
}

it's something like that. 就是这样 The datatable has more than a thousand rows and the functions has to be called nearly a thousand times when the asp.net page loads. 数据表具有一千多行,并且在asp.net页面加载时必须调用该函数近一千次。

So i have to change it. 所以我必须改变它。

i considered using dictionary but it seems that it takes only two variables. 我考虑使用字典,但似乎只需要两个变量。 What can you suggest me. 你能建议我什么。

Edit: 编辑:

I could not solve the problem yet. 我还不能解决问题。 Here is the related code. 这是相关的代码。 Thanks in advance. 提前致谢。

protected void RadScheduler_Randevu_TimeSlotCreated(object sender, Telerik.Web.UI.TimeSlotCreatedEventArgs e) { 受保护的void RadScheduler_Randevu_TimeSlotCreated(对象发送者,Telerik.Web.UI.TimeSlotCreatedEventArgs e){

for (int i = 0; i < calismaSaatleridt.Rows.Count; i++)
{
    if (RadScheduler_Randevu.SelectedView.Equals(SchedulerViewType.DayView))
    {
        if (RadScheduler_Randevu.SelectedDate.ToShortDateString().Equals(Convert.ToDateTime(calismaSaatleridt.Rows[i]["calisma_baslangic"]).ToShortDateString()))
        {
            if (e.TimeSlot.Resource.Key.ToString().Equals(calismaSaatleridt.Rows[i]["hekim_id"].ToString()))
            {
                if (DateTime.Compare(e.TimeSlot.Start, Convert.ToDateTime(calismaSaatleridt.Rows[i]["calisma_baslangic"])) < 0 || DateTime.Compare(e.TimeSlot.End, Convert.ToDateTime(calismaSaatleridt.Rows[i]["calisma_bitis"])) > 0)
                {
                    e.TimeSlot.CssClass = "Disabled";
                }
            }
        }
    }
}

} }

This is the function that returns the result set. 这是返回结果集的函数。

private DataTable calismaSaatiGetir(string yonetici_id)
    {
        SqlConnection connection = new SqlConnection();
        connection.ConnectionString = ConfigurationManager.ConnectionStrings["ConnectionString"].ConnectionString;
        SqlCommand command = new SqlCommand();
        command.CommandText = "select calisma_saati.id,kullanici.id as hekim_id,LEFT(CONVERT(VARCHAR,calisma_saati.tarih,104),10)+ ' ' +LEFT(CONVERT(VARCHAR,calisma_saati.baslangic_saati,108),5) AS calisma_baslangic,LEFT(CONVERT(VARCHAR,calisma_saati.tarih,104),10)+ ' '+LEFT(CONVERT(VARCHAR,calisma_saati.bitis_saati,108),5) AS calisma_bitis from calisma_saati JOIN kullanici ON kullanici.id=calisma_saati.kullanici_id WHERE  yonetici_id='" +  Session["yonetici"].ToString() + "' ";
        command.Connection = connection;
        connection.Open();
        SqlDataAdapter da = new SqlDataAdapter(command.CommandText, connection);
        DataSet ds = new DataSet();
        da.Fill(ds, "calisma_saati");
        calismaSaatleridt = ds.Tables["calisma_saati"];
        connection.Close(); 
        return calismaSaatleridt;
    }

The datatable has more than a thousand rows and the functions has to be called nearly a thousand times 数据表具有一千多行,并且函数必须调用近一千次

There's your problem. 有你的问题。 If I'm reading that right, you're looping through the entire datatable for every item in some other collection of data that isn't shown in the question. 如果我没看错,那么您正在遍历整个数据表,查找问题中未显示的其他数据集中的每个项目。

The best way to fix this is at the database level: whatever you're doing to generate this datatable needs to know about your other data set so you can take it into account on the database (and make use of things like indexes and cached data). 解决此问题的最佳方法是在数据库级别:生成此数据表的任何操作都需要了解其他数据集,以便可以在数据库中加以考虑(并利用索引和缓存数据之类的东西) )。 That might mean writing a select query that is much more complicated than what you're used to, but it's the right way to do this. 这可能意味着编写一个选择查询,该查询比您以前习惯的要复杂得多,但这是正确的选择。

If this just isn't an option, you still want to re-work this in some way so that you only interate through everything once. 如果这不是一个选择,那么您仍然希望以某种方式对其进行重新处理,以使您仅对所有内容进行一次交互。 If you're using c#, you can probably accomplish that via a linq query (or even just the IEnumerable extensions + lambda methods). 如果您使用的是c#,则可以通过linq查询(甚至只是IEnumerable扩展名+ lambda方法)来实现。

Regarding using a dictionary: it may take only two variables, but one of those variables could be a more-complicated object, like an entire datarow from your table. 关于使用字典:它可能只包含两个变量,但是其中一个变量可能是一个更复杂的对象,例如表中的整个数据行。 Either way, to give you anything like sample code we need a better idea of what that other data looks like and what your intended result is. 无论哪种方式,要给您类似示例代码的东西,我们都需要更好地了解其他数据的外观以及预期的结果。

Is this coming from a database directly? 这是直接来自数据库吗? If so, why not just perform a query to get a more specific result set? 如果是这样,为什么不执行查询以获得更具体的结果集呢? Then you could use linq to get execute your function on each row. 然后,您可以使用linq在每一行上执行函数。

More defined SQL: select * from table where userID = 'bob' and starttime between '1/1/2009 11:00 PM' and '1/1/2009 11:21 PM' 更定义的SQL:从其中userID ='bob'的表中选择*,并在'1/1/2009 11:00 PM'和'1/1/2009 11:21 PM'之间开始时间

Linq: Linq:

DataTable table = getFromDb();
table.Rows.Cast<DataRow>().ToList().ForEach(x => RunMyFunction(x));

void RunMyFunction(DataRow row)
{

}

how about this? 这个怎么样? (it would be better if you could push this query to the database. but this will be faster than looping every row) (如果您可以将此查询推送到数据库,会更好。但这比循环每一行要快)

void something(DataTable dt, myobj Someobject, DateTime somevariable)
{
    string filterPattern = "user_id='{0}' AND starttime='{1}'";
    string filter = string.Format(filterPattern, 
                                  Someobject.variable, 
                                  somevariable);
    DataRow[] rows = dt.Select(filter);

    foreach (DataRow row in rows)
        DoSomething(row);
}
void DoSomething(DataRow row)
{
}
public class myobj
{
    public string variable { get; set; }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM