如何防止程序重复运行

takpod 2015-05-16 09:13:10
        private void Form1_Load(object sender, EventArgs e)
{
Process[] ProcessColection = Process.GetProcessesByName(Application.CompanyName);
if (ProcessColection.Length >= 1)
{
MessageBox.Show("程序已经运行!");
Thread.Sleep(1000);
System.Environment.Exit(1);
}
}


当我第二次启动是还是出现 停止工作的对话框 而不是上面的对话框,请问这些代码要加在哪里呢?
...全文
517 19 打赏 收藏 转发到动态 举报
写回复
用AI写文章
19 条回复
切换为时间正序
请发表友善的回复…
发表回复
於黾 2015-05-18
  • 打赏
  • 举报
回复
1.你写>=1,那么即使之前没有进程在运行,你这个进程一运行起来,就等于1了,那么它自己就退出了! 2.program类里有主函数的入口,你应该写在入口函数里,而不是写到窗体代码里
SadlyCodes 2015-05-18
  • 打赏
  • 举报
回复

        static bool AnotherIsRunning()
        {
            bool flag;
            var mutex = new Mutex(true, "abc", out flag);
            return !flag;
        }
返回true表示有正在运行的程序否则是没有
marswangbo 2015-05-17
  • 打赏
  • 举报
回复
还有,这个不要放在 LOAD里面。。放在入口里面。PROGRAM.cs
marswangbo 2015-05-17
  • 打赏
  • 举报
回复
>=1。。。改成>1
Imcx 2015-05-17
  • 打赏
  • 举报
回复
引用 5 楼 takpod 的回复:
[quote=引用 3 楼 yanran_hill 的回复:] [quote=引用 楼主 takpod 的回复:]
        private void Form1_Load(object sender, EventArgs e)
        {
            Process[] ProcessColection = Process.GetProcessesByName(Application.CompanyName);
            if (ProcessColection.Length >= 1)
            {
              ...
            }
}
方法应该很多,不过我个人认为:通过获取进程名的方式判断是比较笨的一种,这么做比较复杂,开发成本较高 通常我是这样做的 :程序运行后,创建一个.pid文件,并锁住这个文件,如果失败了,就提示说进程在运行。
第二次运行程序还没有form_load时就死了,我的代码应该加在哪里呢?我的是WinFromApp[/quote] 在程序入口文件里啊,默认名字是Program.cs,就是在你的窗体项目里面
angshuangxi1 2015-05-17
  • 打赏
  • 举报
回复
我自己用的函数: 使用方法: if (ProgramIsStarted(Assembly.GetExecutingAssembly().GetName().Name)) { MessageBox.Show("程序已经启动!", "错误提示"); Environment.Exit(0); return; } public static bool ProgramIsStarted(string progName) { Process currProcess = Process.GetCurrentProcess(); if (currProcess == null) return false; Process[] processOnComputer = Process.GetProcesses(); foreach (Process p in processOnComputer) { if (progName.Equals(p.ProcessName, StringComparison.OrdinalIgnoreCase) && p.Id != currProcess.Id) return true; } return false; }
  • 打赏
  • 举报
回复
这个方法很多,需要根据你自己的需要来判断
devmiao 2015-05-16
  • 打赏
  • 举报
回复
标准的做法是使用互斥量判断
  • 打赏
  • 举报
回复
引用 5 楼 takpod 的回复:
第二次运行程序还没有form_load时就死了,我的代码应该加在哪里呢?我的是WinFromApp
直接判断是否有进程正在运行,不要绕别的容易出错的路上去。
s_hhm 2015-05-16
  • 打赏
  • 举报
回复
[quote=引用 5 楼 takpod 的回复:] [quote=引用 3 楼 yanran_hill 的回复:] [quote=引用 楼主 takpod 的回复:]
        private void Form1_Load(object sender, EventArgs e)
        {
            Process[] ProcessColection = Process.GetProcessesByName(Application.CompanyName);
            if (ProcessColection.Length >= 1)
            {
              ...
            }
}
方法应该很多,不过我个人认为:通过获取进程名的方式判断是比较笨的一种,这么做比较复杂,开发成本较高 通常我是这样做的 :程序运行后,创建一个.pid文件,并锁住这个文件,如果失败了,就提示说进程在运行。 这样不行吧,如果我把程序分别放在两个目录.就可以再次创建文件了.因为文件不存在应该是要新建的嘛.还是判断进程实例比较好.具体 方法度娘那大把
江南小鱼 2015-05-16
  • 打赏
  • 举报
回复
引用 楼主 takpod 的回复:
        private void Form1_Load(object sender, EventArgs e)
        {
            Process[] ProcessColection = Process.GetProcessesByName(Application.CompanyName);
            if (ProcessColection.Length >= 1)
            {
                MessageBox.Show("程序已经运行!");
                Thread.Sleep(1000);
                System.Environment.Exit(1);
            }
}
当我第二次启动是还是出现 停止工作的对话框 而不是上面的对话框,请问这些代码要加在哪里呢?
引用 楼主 takpod 的回复:
        private void Form1_Load(object sender, EventArgs e)
        {
            Process[] ProcessColection = Process.GetProcessesByName(Application.CompanyName);
            if (ProcessColection.Length >= 1)
            {
                MessageBox.Show("程序已经运行!");
                Thread.Sleep(1000);
                System.Environment.Exit(1);
            }
}
当我第二次启动是还是出现 停止工作的对话框 而不是上面的对话框,请问这些代码要加在哪里呢?
把大于等于1,改成大于1
ProcessColection.Length > 1
takpod 2015-05-16
  • 打赏
  • 举报
回复
引用 3 楼 yanran_hill 的回复:
[quote=引用 楼主 takpod 的回复:]
        private void Form1_Load(object sender, EventArgs e)
        {
            Process[] ProcessColection = Process.GetProcessesByName(Application.CompanyName);
            if (ProcessColection.Length >= 1)
            {
              ...
            }
}
方法应该很多,不过我个人认为:通过获取进程名的方式判断是比较笨的一种,这么做比较复杂,开发成本较高 通常我是这样做的 :程序运行后,创建一个.pid文件,并锁住这个文件,如果失败了,就提示说进程在运行。
第二次运行程序还没有form_load时就死了,我的代码应该加在哪里呢?我的是WinFromApp
takpod 2015-05-16
  • 打赏
  • 举报
回复
引用 1 楼 yangb0803 的回复:


using System;  
using System.Collections.Generic;  
using System.Windows.Forms;  
using System.Diagnostics;  
  
namespace TestProcessCount  
{  
    static class Program  
    {  
        /// <summary>  
        /// The main entry point for the application.  
        /// </summary>  
        [STAThread]  
        static void Main()  
        {  
            int processCount = 0;  
            Process[] pa = Process.GetProcesses();//获取当前进程数组。  
            foreach (Process PTest in pa)  
            {  
                if (PTest.ProcessName == Process.GetCurrentProcess().ProcessName)  
                {  
                    processCount += 1;  
                }  
            }  
            if (processCount > 1)  
            {  
                //如果程序已经运行,则给出提示。并退出本进程。  
                DialogResult dr;  
                dr = MessageBox.Show( Process.GetCurrentProcess().ProcessName+"程序已经在运行!", "退出程序", MessageBoxButtons.OK, MessageBoxIcon.Error);  
//可能你不需要弹出窗口,在这里可以屏蔽掉  
                return; //Exit;  
                
            }  
            Application.EnableVisualStyles();  
            Application.SetCompatibleTextRenderingDefault(false);  
            Application.Run(new frmBrowser());  
        }  
    }  
}

问题是我不知把代码加在哪里~启动第二个程序时还没有运行到form_load时就停止运行了
allen0118 2015-05-16
  • 打赏
  • 举报
回复
      #region 检测当前窗体是否处于运行状态
        private static Mutex mutex = null;
        /// <summary>
        /// 检测当前窗体是否处于运行状态
        /// </summary>
        private static void GlobalMutex()
        {
            // 是否第一次创建mutex
            bool newMutexCreated = false;
            string mutexName = "Global\\" + "Allen.Tool";//系统名称,Global为全局,表示即使通过通过虚拟桌面连接过来,也只是允许运行一次
            try
            {
                mutex = new Mutex(false, mutexName, out newMutexCreated);
            }
            catch (Exception ex)
            {
                Console.Write(ex.Message);
                System.Threading.Thread.Sleep(1000);
                Environment.Exit(1);
            }

            // 第一次创建mutex
            if (newMutexCreated)
            {
                Console.WriteLine("程序已启动");
                //todo:此处为要执行的任务
            }
            else
            {
                MessageBox.Show("检测到另一个窗口已处于运行状态,不能重复运行。", "温馨提示", MessageBoxButtons.OK, MessageBoxIcon.Information);
                System.Threading.Thread.Sleep(1000);
                Environment.Exit(1);//退出程序
            }
        }
        #endregion
yanran_hill 2015-05-16
  • 打赏
  • 举报
回复
[quote=引用 楼主 takpod 的回复:]
        private void Form1_Load(object sender, EventArgs e)
        {
            Process[] ProcessColection = Process.GetProcessesByName(Application.CompanyName);
            if (ProcessColection.Length >= 1)
            {
              ...
            }
}
方法应该很多,不过我个人认为:通过获取进程名的方式判断是比较笨的一种,这么做比较复杂,开发成本较高 通常我是这样做的 :程序运行后,创建一个.pid文件,并锁住这个文件,如果失败了,就提示说进程在运行。
道玄希言 2015-05-16
  • 打赏
  • 举报
回复

static class Program
    {
        /// <summary>
        /// The main entry point for the application.
        /// </summary>
        [STAThread]
        static void Main()
        {
            bool createdNew;
            //系统能够识别有名称的互斥,因此可以使用它禁止应用程序启动两次
            //第二个参数可以设置为产品的名称:Application.ProductName
            //每次启动应用程序,都会验证名称为SingletonWinAppMutex的互斥是否存在
            Mutex mutex = new Mutex(false, "SingletonWinAppMutex", out createdNew);

            //如果已运行,则在前端显示
            //createdNew == false,说明程序已运行
            if (!createdNew)
            {
                Process instance = GetExistProcess();
                if (instance != null)
                {
                    SetForegroud(instance);
                    Application.Exit();
                    return;
                }
            }
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new MainForm());
        }
        /// <summary>
        /// 查看程序是否已经运行
        /// </summary>
        /// <returns></returns>
        private static Process GetExistProcess()
        {
            Process currentProcess = Process.GetCurrentProcess();
            foreach (Process process in Process.GetProcessesByName(currentProcess.ProcessName))
            {
                if ((process.Id != currentProcess.Id) && 
                    (Assembly.GetExecutingAssembly().Location == currentProcess.MainModule.FileName))
                {
                    return process;
                }
            }
            return null;
        }
        /// <summary>
        /// 使程序前端显示
        /// </summary>
        /// <param name="instance"></param>
        private static void SetForegroud(Process instance)
        {
            IntPtr mainFormHandle = instance.MainWindowHandle;
            if (mainFormHandle != IntPtr.Zero)
            {
                ShowWindowAsync(mainFormHandle, 1);
                SetForegroundWindow(mainFormHandle);
            }
        }
        [DllImport("User32.dll")]
        private static extern bool SetForegroundWindow(IntPtr hWnd);
        [DllImport("User32.dll")]
        private static extern bool ShowWindowAsync(IntPtr hWnd, int cmdShow);
    }
道玄希言 2015-05-16
  • 打赏
  • 举报
回复


using System;  
using System.Collections.Generic;  
using System.Windows.Forms;  
using System.Diagnostics;  
  
namespace TestProcessCount  
{  
    static class Program  
    {  
        /// <summary>  
        /// The main entry point for the application.  
        /// </summary>  
        [STAThread]  
        static void Main()  
        {  
            int processCount = 0;  
            Process[] pa = Process.GetProcesses();//获取当前进程数组。  
            foreach (Process PTest in pa)  
            {  
                if (PTest.ProcessName == Process.GetCurrentProcess().ProcessName)  
                {  
                    processCount += 1;  
                }  
            }  
            if (processCount > 1)  
            {  
                //如果程序已经运行,则给出提示。并退出本进程。  
                DialogResult dr;  
                dr = MessageBox.Show( Process.GetCurrentProcess().ProcessName+"程序已经在运行!", "退出程序", MessageBoxButtons.OK, MessageBoxIcon.Error);  
//可能你不需要弹出窗口,在这里可以屏蔽掉  
                return; //Exit;  
                
            }  
            Application.EnableVisualStyles();  
            Application.SetCompatibleTextRenderingDefault(false);  
            Application.Run(new frmBrowser());  
        }  
    }  
}

失落的神庙 2015-05-16
  • 打赏
  • 举报
回复
引用 9 楼 johnliuyuan 的回复:
[quote=引用 2 楼 yangb0803 的回复:]

static class Program
    {
        /// <summary>
        /// The main entry point for the application.
        /// </summary>
        [STAThread]
        static void Main()
        {
            bool createdNew;
            //系统能够识别有名称的互斥,因此可以使用它禁止应用程序启动两次
            //第二个参数可以设置为产品的名称:Application.ProductName
            //每次启动应用程序,都会验证名称为SingletonWinAppMutex的互斥是否存在
            Mutex mutex = new Mutex(false, "SingletonWinAppMutex", out createdNew);

            //如果已运行,则在前端显示
            //createdNew == false,说明程序已运行
            if (!createdNew)
            {
                Process instance = GetExistProcess();
                if (instance != null)
                {
                    SetForegroud(instance);
                    Application.Exit();
                    return;
                }
            }
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new MainForm());
        }
        /// <summary>
        /// 查看程序是否已经运行
        /// </summary>
        /// <returns></returns>
        private static Process GetExistProcess()
        {
            Process currentProcess = Process.GetCurrentProcess();
            foreach (Process process in Process.GetProcessesByName(currentProcess.ProcessName))
            {
                if ((process.Id != currentProcess.Id) && 
                    (Assembly.GetExecutingAssembly().Location == currentProcess.MainModule.FileName))
                {
                    return process;
                }
            }
            return null;
        }
        /// <summary>
        /// 使程序前端显示
        /// </summary>
        /// <param name="instance"></param>
        private static void SetForegroud(Process instance)
        {
            IntPtr mainFormHandle = instance.MainWindowHandle;
            if (mainFormHandle != IntPtr.Zero)
            {
                ShowWindowAsync(mainFormHandle, 1);
                SetForegroundWindow(mainFormHandle);
            }
        }
        [DllImport("User32.dll")]
        private static extern bool SetForegroundWindow(IntPtr hWnd);
        [DllImport("User32.dll")]
        private static extern bool ShowWindowAsync(IntPtr hWnd, int cmdShow);
    }
这个方法比较好[/quote] 当然是互斥锁好。
john_QQ:2335298917 2015-05-16
  • 打赏
  • 举报
回复
引用 2 楼 yangb0803 的回复:

static class Program
    {
        /// <summary>
        /// The main entry point for the application.
        /// </summary>
        [STAThread]
        static void Main()
        {
            bool createdNew;
            //系统能够识别有名称的互斥,因此可以使用它禁止应用程序启动两次
            //第二个参数可以设置为产品的名称:Application.ProductName
            //每次启动应用程序,都会验证名称为SingletonWinAppMutex的互斥是否存在
            Mutex mutex = new Mutex(false, "SingletonWinAppMutex", out createdNew);

            //如果已运行,则在前端显示
            //createdNew == false,说明程序已运行
            if (!createdNew)
            {
                Process instance = GetExistProcess();
                if (instance != null)
                {
                    SetForegroud(instance);
                    Application.Exit();
                    return;
                }
            }
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new MainForm());
        }
        /// <summary>
        /// 查看程序是否已经运行
        /// </summary>
        /// <returns></returns>
        private static Process GetExistProcess()
        {
            Process currentProcess = Process.GetCurrentProcess();
            foreach (Process process in Process.GetProcessesByName(currentProcess.ProcessName))
            {
                if ((process.Id != currentProcess.Id) && 
                    (Assembly.GetExecutingAssembly().Location == currentProcess.MainModule.FileName))
                {
                    return process;
                }
            }
            return null;
        }
        /// <summary>
        /// 使程序前端显示
        /// </summary>
        /// <param name="instance"></param>
        private static void SetForegroud(Process instance)
        {
            IntPtr mainFormHandle = instance.MainWindowHandle;
            if (mainFormHandle != IntPtr.Zero)
            {
                ShowWindowAsync(mainFormHandle, 1);
                SetForegroundWindow(mainFormHandle);
            }
        }
        [DllImport("User32.dll")]
        private static extern bool SetForegroundWindow(IntPtr hWnd);
        [DllImport("User32.dll")]
        private static extern bool ShowWindowAsync(IntPtr hWnd, int cmdShow);
    }
这个方法比较好

110,536

社区成员

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

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

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