0

データセットに ReferenceID (文字列) のリストがあります。These ReferenceIDs can have values like this ("CQ1258891","CQ1258892","CQ1258893"....""CQ1258993"). 私のコードには、各 ReferenceID に対してメールを送信するロジックがあります。

今のところ、すべての ReferenceID を同期的にループしています。そのため、すべてのメールを送信するのに時間がかかります。私は .NET 3.0 を使用しているため、.NET 4.0 で TPL を使用するオプションがありません。

私は、すべての ReferenceID のメールを非同期的に送信するためのマルチスレッド メカニズムを探していました。現在、次のコードを試しましたが、期待どおりに動作しません。

foreach (DataRow row in qrefSet.Tables[0].Rows)
{
    string refId = Convert.ToString(row["ReferenceID"]);
    if (!string.IsNullOrEmpty(refId))
    {
        Thread thread = new Thread(() => apeDBAdapter.SendEmail(personId, refId, parentReferenceID, customerName, queueId));                                    
        thread.Start();
    }
}

私の実装でマルチスレッド foreach ループを実現するための効果的なメカニズムを共有してください。

ありがとう、スリラム

4

3 に答える 3

2

これを試して

foreach (DataRow row in qrefSet.Tables[0].Rows)
{
    string refId = Convert.ToString(row["ReferenceID"]);
    if (!string.IsNullOrEmpty(refId))
    {
        Thread thread = new Thread(new ParameterizedThreadStart(SendMail));
        thread.Start(refId)           
    }
}
..........
void SendMail(object refId)
{
    string strRefId = (string)refId;
    apeDBAdapter.SendEmail(personId, refId, parentReferenceID, customerName, queueId));  
}

それが役に立てば幸い...

于 2013-10-16T06:46:11.400 に答える
0

この構造を使用してそれを行うことができます。ThreadPool を使用しているため、多くのスレッドを作成していませんが、 APM を使用して電子メールを送信することをお勧めします。したがって、スレッドが無駄になることはありません。

すべてのバックグラウンド操作が完了するまで待機します。はdata、データセットの行です。

int opsLeft = data.Count();
using (var mre = new ManualResetEvent(false))
{
    foreach (DataRow row in data)
    {
        string refId = Convert.ToString(row["ReferenceID"]);
        if (!string.IsNullOrEmpty(refId))
        {
            ThreadPool.QueueUserWorkItem(_ =>
            {
                apeDBAdapter.SendEmail(personId, refId, parentReferenceID, customerName, queueId);
                if (Interlocked.Decrement(ref opsLeft) == 0)
                    mre.Set();
            });
        }
        else
        {
            if (Interlocked.Decrement(ref opsLeft) == 0)
                mre.Set();
        }
    }
    mre.WaitOne();
}
于 2013-10-16T11:20:34.227 に答える
0

行コレクションから一定範囲のアイテムを取得し、分割数に応じてマルチスレッドで実行するメソッドを作成できます。

例えば:

SendEmailsToReferencesByRange(int start, int end, DataRowCollection rows)
{
  foreach(var item in rows.Range(start, end-start))
  {
     //Do your sending logic here
  }
}

使用法:

//if for example you have 200 items than you can run it in 2 threads
Thread thread = new Thread(()=>SendEmailsToReferencesByRange(0,100, table[0].Rows)).Start();
Thread thread = new Thread(()=>SendEmailsToReferencesByRange(100,200, table[0].Rows)).Start();
于 2013-10-16T06:46:55.280 に答える