多线程问题,请教各位大大们解答!

鬼五拾柒 2015-04-04 08:09:29
我要实现一个先从数据库里读取所有电脑IP 取出来Ping,然后根据Ping结果来修改这张表的某一列,如何写。
...全文
255 17 打赏 收藏 转发到动态 举报
写回复
用AI写文章
17 条回复
切换为时间正序
请发表友善的回复…
发表回复
江南小鱼 2015-04-04
  • 打赏
  • 举报
回复
引用 楼主 u011683479 的回复:
我要实现一个先从数据库里读取所有电脑IP 取出来Ping,然后根据Ping结果来修改这张表的某一列,如何写。
你这个需求和多线程没神马关系 1、从数据库取出所有ip,塞到一个List<string>里面,比如lstAll 2、遍历lstAll,执行ping,然后修改数据库 当然,考虑提供效率,开启多个线程对List<string>里的元素进行ping 参考ThreadPool
鬼五拾柒 2015-04-04
  • 打赏
  • 举报
回复
引用 5 楼 xuzuning 的回复:
这与是否多线程并没有关系 你只是: 1、查询数据库 2、循环查到的结果 2.1 对每一个结果执行 ping 2.2 根据返回的结果修改数据库 3、结束 这是单线程 多线程就是:在循环中开线程,执行 2.1、2.2
那么执行 2.1,2.2这2个步骤该如何写呢。
本拉灯 2015-04-04
  • 打赏
  • 举报
回复
定义实体 属性如下: 表主ID,IP 提取表中所有IP数据(用上面的实体) 放到Queue队例(ipQueue)中 然后线程Thread定义两个或N个 线程调用的方法里 如下 void Proc() { while(ipQueue.Count>0) { lock(ipQueue) { 实体= ipQueue.Dequeue(); 结果= 这里Pin 实体.IP; 更新 表 set xxx=结果 where 表主ID=实体.主ID } } }
xuzuning 2015-04-04
  • 打赏
  • 举报
回复
这与是否多线程并没有关系 你只是: 1、查询数据库 2、循环查到的结果 2.1 对每一个结果执行 ping 2.2 根据返回的结果修改数据库 3、结束 这是单线程 多线程就是:在循环中开线程,执行 2.1、2.2
鬼五拾柒 2015-04-04
  • 打赏
  • 举报
回复
引用 3 楼 wyd1520 的回复:
求教啊,多线程一点都不会
鬼五拾柒 2015-04-04
  • 打赏
  • 举报
回复
求教各位,这个多线程如何写
  • 打赏
  • 举报
回复
多线程建议用Task来做,好象微软提倡用着东西代替传统的threading,取ping的结果用Process类,具体查一下如何在c#里执行命令行程序及取执行结果,不复杂。
  • 打赏
  • 举报
回复
引用 15 楼 u011683479 的回复:
这样说得我模棱两可了
如果你觉得越是底层的东西越“好”,越是低级的东西越清楚,那么你就去折腾那些模棱两可的东西吧。那些底层的东西正因为被许多人说得模棱两可,所以你才觉得“看起来很厉害似地”。 而我首先强调的是一个人的开发能力。先是“用2、3行代码非常正确地实现并发计算”的能力有了,等你有闲功夫的时候,你用你已经并发工作很好的程序来检验别人给你说的底层的东西,你就自己就能知道其有没有必要折腾那些语句了!
  • 打赏
  • 举报
回复
在你的范畴中,什么Thread、Task、Queue、lock 等等,都是浮云,都是编程的干扰因素。 .net framework 没有那么低级,并不需要你一开始就研究什么底层(更何况有时候所生搬硬套来的所谓数据结构、循环处理流程,有很多都是没有必要或者干脆是阻碍了并行化的)。 不需要为了时髦而使用 Thread、Task。多线程并发处理首先是调用一下 AsParallel() 函数就行了,你起码要把这个熟练掌握了(就好像掌握基本的流程控制语句一样)。这是务实而直接的入门学习方法。 这就好像有的人只学过 c 就套用到 c# 上而写了一本 c# (甚至.net平台)编程开发的书,那么这本书一定是会误导许多c#初学者的。同样地,拿那些根本没有 PLinq 等等框架的比较低级的编程框架平台的概念来套用在你的工作中,太早、太技术化,并不会带来什么好处。
鬼五拾柒 2015-04-04
  • 打赏
  • 举报
回复
引用 13 楼 sp1234 的回复:
多线程并发查询数据应该使用 PLInq 来写。 首先,需要将你的查询操作变为函数:
public static bool PingIP(string ip, int id)
{
    Ping pingSender = new Ping();
    //PingReply reply = 
    PingReply reply = pingSender.Send(ip, 120);
    if (reply.Status == IPStatus.Success)
    {
        //ping的通 
        string upIp = "UPDATE t_jl0020_pst_no set ping_ok='N' where id_num=@id_num";
        SqlParameter[] par = new SqlParameter[] 
            {
                    new SqlParameter("@id_num",id)
            };
        SQLHelper.Update(upIp, par);
        return true;
    }
    else
    {
        //ping不通            
        string upIp = "UPDATE t_jl0020_pst_no set ping_ok='N' where id_num=@id_num";
        SqlParameter[] par = new SqlParameter[] 
            {
                    new SqlParameter("@id_num",id)
            };
        SQLHelper.Update(upIp, par);
        return false;
    }
}

}
然后统计函数返回值
DataTable dt = SQLHelper.SelectTable("select id_num,com_ip from t_jl0020_pst_no");
var result = (from row in dt.Rows.Cast<DataRow>().AsParallel()
                let ip = (string)row["com_ip"]
                let id = int.Parse((string)row["_id_num"])
                select new { ip, id, result = PingIP(ip, id) }).ToList();
这样就知道数据库表中都有哪些ip、id,以及并发(AsParallel)计算结果。
这样说得我模棱两可了
  • 打赏
  • 举报
回复
当然,要使用 PLinq,跟Linq一样,都是需要
using System.Linq;
我以前强调过,一些人把线程说得很时髦,但是却又非常奇怪、非常繁冗和效率低下的复杂程序格式,造成了初学者根本不会书写并发多线程计算程序。那种东西还是知道得越少越好。 如果需要使用到什么Thread之类的,那是需要你去设计比较高级一些的应用程序的时候(例如需要在 t_jl0020_pst_no 表所标记的 ip 中只找到 Ping 响应最快的3条记录,而不需要等待所有结果返回)。否则,如果是这样简单的程序编写工作,那么我建议程序员不要去过多揪扯什么底层的东西,先把 PLinq 基本语法学会比什么理论都强。
  • 打赏
  • 举报
回复
多线程并发查询数据应该使用 PLInq 来写。 首先,需要将你的查询操作变为函数:
public static bool PingIP(string ip, int id)
{
    Ping pingSender = new Ping();
    //PingReply reply = 
    PingReply reply = pingSender.Send(ip, 120);
    if (reply.Status == IPStatus.Success)
    {
        //ping的通 
        string upIp = "UPDATE t_jl0020_pst_no set ping_ok='N' where id_num=@id_num";
        SqlParameter[] par = new SqlParameter[] 
            {
                    new SqlParameter("@id_num",id)
            };
        SQLHelper.Update(upIp, par);
        return true;
    }
    else
    {
        //ping不通            
        string upIp = "UPDATE t_jl0020_pst_no set ping_ok='N' where id_num=@id_num";
        SqlParameter[] par = new SqlParameter[] 
            {
                    new SqlParameter("@id_num",id)
            };
        SQLHelper.Update(upIp, par);
        return false;
    }
}

}
然后统计函数返回值
DataTable dt = SQLHelper.SelectTable("select id_num,com_ip from t_jl0020_pst_no");
var result = (from row in dt.Rows.Cast<DataRow>().AsParallel()
                let ip = (string)row["com_ip"]
                let id = int.Parse((string)row["_id_num"])
                select new { ip, id, result = PingIP(ip, id) }).ToList();
这样就知道数据库表中都有哪些ip、id,以及并发(AsParallel)计算结果。
鬼五拾柒 2015-04-04
  • 打赏
  • 举报
回复
引用 11 楼 wyd1520 的回复:
lm 不能定义为List<xxx> 应定义为Queue<xxx> lock (lm) { IPModel m=lm.Dequeue(); 这里下面处理 PIn操作 }
还是不对呀,这样只改了第一条数据
本拉灯 2015-04-04
  • 打赏
  • 举报
回复
lm 不能定义为List<xxx> 应定义为Queue<xxx> lock (lm) { IPModel m=lm.Dequeue(); 这里下面处理 PIn操作 }
鬼五拾柒 2015-04-04
  • 打赏
  • 举报
回复
引用 6 楼 wyd1520 的回复:
定义实体 属性如下: 表主ID,IP 提取表中所有IP数据(用上面的实体) 放到Queue队例(ipQueue)中 然后线程Thread定义两个或N个 线程调用的方法里 如下 void Proc() { while(ipQueue.Count>0) { lock(ipQueue) { 实体= ipQueue.Dequeue(); 结果= 这里Pin 实体.IP; 更新 表 set xxx=结果 where 表主ID=实体.主ID } } }

  private void ZXGC_Load(object sender, EventArgs e)
        {
            SelectIP();
            int line_count = lm.Count;
            Thread[] line_PING = new Thread[line_count];
            foreach (IPModel ipm in lm)
            {
                for (int i = 0; i < line_count; i++)
                {
                    line_PING[i] = new Thread(delegate() { PingIP(ipm.ipAd, ipm.id); });
                    line_PING[i].Start();
                    MessageBox.Show("线程"+i+"正在执行!");
                }
            }           
       }


        /// <summary>
        /// pingIP地址
        /// </summary>
        public void PingIP(string ip, int id)
        {
            while (lm.Count > 0)
            {
                lock (lm)
                {
                    Ping pingSender = new Ping();
                    //PingReply reply = 
                    PingReply reply = pingSender.Send(ip, 10);
                    if (reply.Status == IPStatus.Success)
                    {
                        //ping的通 
                       // MessageBox.Show("OK");
                        string upIp = "UPDATE t_jl0020_pst_no set ping_ok='Y' where id_num=@id_num";
                        SqlParameter[] par = new SqlParameter[] 
                    {
                         new SqlParameter("@id_num",id)
                    };
                        SQLHelper.Update(upIp, par);

                    }
                    else
                    {
                        //ping不通    
                       // MessageBox.Show("No!");
                        string upIp = "UPDATE t_jl0020_pst_no set ping_ok='N' where id_num=@id_num";
                        SqlParameter[] par = new SqlParameter[] 
                    {
                         new SqlParameter("@id_num",id)
                    };
                        SQLHelper.Update(upIp, par);
                    }
                }
            }
        }
        /// <summary>
        /// 获取车间所有测试机的IP地址
        /// </summary>
        public void SelectIP()
        {
            DataTable dt = SQLHelper.SelectTable("select id_num,com_ip from t_jl0020_pst_no");
            for (int i = 0; i < dt.Rows.Count; i++)
            {
                IPModel im = new IPModel();
                im.id = Convert.ToInt32(dt.Rows[i][0].ToString());
                im.ipAd = dt.Rows[i][1].ToString();
                lm.Add(im);
            }
           
        }
就修改了3条数据
鬼五拾柒 2015-04-04
  • 打赏
  • 举报
回复
引用 6 楼 wyd1520 的回复:
定义实体 属性如下: 表主ID,IP 提取表中所有IP数据(用上面的实体) 放到Queue队例(ipQueue)中 然后线程Thread定义两个或N个 线程调用的方法里 如下 void Proc() { while(ipQueue.Count>0) { lock(ipQueue) { 实体= ipQueue.Dequeue(); 结果= 这里Pin 实体.IP; 更新 表 set xxx=结果 where 表主ID=实体.主ID } } }

    public void PingIP(string ip,int id) 
        {
            Ping pingSender = new Ping();
            //PingReply reply = 
            PingReply reply = pingSender.Send(ip, 120);
            if (reply.Status == IPStatus.Success)
            {
                //ping的通 
                string upIp = "UPDATE t_jl0020_pst_no set ping_ok='N' where id_num=@id_num";
                SqlParameter[] par = new SqlParameter[] 
                    {
                         new SqlParameter("@id_num",id)
                    };
                SQLHelper.Update(upIp, par);
                
            }
            else
            {
                //ping不通            
                string upIp = "UPDATE t_jl0020_pst_no set ping_ok='N' where id_num=@id_num";
                SqlParameter[] par = new SqlParameter[] 
                    {
                         new SqlParameter("@id_num",id)
                    };
                SQLHelper.Update(upIp, par);
            }          
        }
       private void ZXGC_Load(object sender, EventArgs e)
        {
            SelectIP();
            int line_count = lm.Count;
            Thread[] line_PING = new Thread[line_count];
            foreach (IPModel ipm in lm)
            {       
                for (int i = 0; i < line_count; i++)
                {
                    line_PING[i] = new Thread(delegate(){ PingIP(ipm.ipAd,ipm.id);});
                    line_PING[i].Start(i);
                }
            }           
       }
       public void SelectIP()
        {
            DataTable dt = SQLHelper.SelectTable("select id_num,com_ip from t_jl0020_pst_no");
            for (int i = 0; i < dt.Rows.Count; i++)
            {
                IPModel im = new IPModel();
                im.id = Convert.ToInt32(dt.Rows[i][0].ToString());
                im.ipAd = dt.Rows[i][1].ToString();
                lm.Add(im);
            } 
        }
       public void SelectIP()
        {
            DataTable dt = SQLHelper.SelectTable("select id_num,com_ip from t_jl0020_pst_no");
            for (int i = 0; i < dt.Rows.Count; i++)
            {
                IPModel im = new IPModel();
                im.id = Convert.ToInt32(dt.Rows[i][0].ToString());
                im.ipAd = dt.Rows[i][1].ToString();
                lm.Add(im);
            }
           
        }
求修改

110,539

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧