• 解决界面卡死的问题


    1.使用多线程

    private void textBox2_TextChanged(object sender, EventArgs e)
    {
        int count = dataGridView1.Rows.GetRowCount(DataGridViewElementStates.Visible);
        Thread objThread = new Thread(new ThreadStart(delegate
        {
            string Temp = textBox2.Text.Trim();
            for (int i = 0; i < count - 1; i++)
            {
                if (!dataGridView1.Rows[i].Cells[0].Value.ToString().ToUpper().Contains(Temp))
                {
                    dataGridView1.Rows[i].Visible = false;
                }
            }
        }));
        objThread.Start();
    }

    添加以下代码,忽略控件多线程的安全机制:(可实现,但不建议直接创建线程操作控件,控件上的大多数方法只能从创建控件的线程调用)

    Control.CheckForIllegalCrossThreadCalls = false;

    也可以使用Invoke

    if(textbox1.InvokeRequired)
    {
        textbox1.Invoke(new MethodInvoker(delegate { name = textbox1.text; }));
    }

    或者使用Task:

    // 首先模拟耗时操作
    private int TaskTest(int num, CancellationToken token)
    {
        // num = 0;
        for (int i = 0; i < int.MaxValue - 10; i++)
        {
            token.ThrowIfCancellationRequested();
            num++;
        }
        return num;
    }
    // 添加了CancellationToken,因而支持取消
    
    // 定义耗时操作完成之后的操作
    private void ShowResult(Task<Int32> t)
    {
        try
        {
            MessageBox.Show(t.Result.ToString());
        }
        catch (AggregateException ex)
        {
            MessageBox.Show("操作中断!");
        }
    }
    
    // 最后是进行异步操作
    Task<Int32> task = new Task<Int32>(n=>TaskTest(10,cancelSource.Token),0);
    task.Start();
    Task tsk = task.ContinueWith(t => ShowResult(t));

    2.使用委托+QueueUserWorkItem

    delegate void ChangeInvoke(int num);
    private void ChangeNum(int num)
    {
        MessageBox.Show(num.ToString());
    }
    private void DoSomeThing(object state)
    {
        int i = 0;
        for (int i = 0; i < int.MaxValue - 1; i++)
        {
            i++;
        }
        ChangeInvoke change = new ChangeInvoke(ChangeNum);
        this.Invoke(change, new object[] { i });
    }

    以下是通过QueueUserWorkItem异步调用

    ThreadPool.QueueUserWorkItem(DoSomeThing);

    3.APM(异步模型)

    // 耗时操作
    private int DoSomeThing(int num)
    {
        for (int i = 0; i < int.MaxValue - 10; i++)
        {
            num++;
        }
        return num;
    }
    // 耗时操作结束后的操作
    private void APMDone(IAsyncResult result)
    {
        var sumDelegate = (Func<int, int>)result.AsyncState;
        try
        {
            int sumResult = sumDelegate.EndInvoke(result);
            MessageBox.Show(sumResult.ToString());
        }
        catch (Exception e)
        {
            MessageBox.Show(e.Message);
        }
    }
    // 最后是调用的方法
    Func<int, int> SumDelegate = TaskTest2;
    SumDelegate.BeginInvoke(0, APMDone, SumDelegate);
  • 相关阅读:
    Android OpenGL(2)
    Bootloader:BareBox
    Android OpenGL(1)
    Android脚本环境
    Android用户界面开发:事件处理
    S5PV210按键控制LED
    S5PV210控制蜂鸣器
    Windows Vista/Windows 7上安装wince5.0/6.0及SDK模拟器
    Makefile
    每日英语:Apps Reorder the Job Landscape
  • 原文地址:https://www.cnblogs.com/jizhiqiliao/p/9870744.html
Copyright © 2020-2023  润新知