`
javasogo
  • 浏览: 1817552 次
  • 性别: Icon_minigender_1
  • 来自: 北京
文章分类
社区版块
存档分类
最新评论

Thread and Sync In C# (C#中的线程与同步)

 
阅读更多

Don't believe everything they've told you. Threads in C# are actually pretty easy.


别相信别人告诉你的所有的事。其实C#中的线程是很简单的。


A thread is an encapsulation of the flow of control in a program. you might be used to writing single-threaded programs - that is, programs that only execute one path through their code "at a time". If you have more than one thread, then code paths run "simultaneously".


线程是程序中的控制流程的封装。你可能已经习惯于写单线程程序,也就是,程序在它们的代码中一次只在一条路中执行。如果你多弄几个线程的话,代码运行可能会更加“同步”。


Why are some phrases above in quotes? In a typical process in which multiple threads exist, zero or more threads may actually be running at any one time. However on a machine that got n CPU's only one thread (actually) can run at any given time on each CPU, because each thread is a code path, each CPU can only run one code-action at a time. The appearance of running many more than n "simultaneously" is done by sharing the CPUs among threads.


在一个有着多线程的典型进程中,零个或更多线程在同时运行。但是,在有着NCPU的机器上,一个线程只能在给定的时间上在一个CPU上运行,因为每个线程都是一个代码段,每个CPU一次只能运行一段代码。而看起来像是N个同时完成是线程间共享CPU时间片的效果。


In this example we will create another thread, we will try to implement a way to demonstrate the multithreaded way of working between the two threads we have, and at the end, we will sync the two threads (the main and the new one) for letting the new thread "wait" for a message before continuing.


这个例子里,我们将创建另一个线程,我们将用两个线程演示多线程的工作方式,最后,我们实现两个线程(主线程与新线程)同步,在新线程工作前必须等待消息。


To create a thread we need to add the System.Threading namespace. After that we need to understand that a thread has GOT to have a start point for its flow of control. The start point is a function, which should be in the same call or in a different one.


建立线程前我们必须引入System.Threading命名空间。然后我需要知道的是,线程得为控制流程建立一个起点。起点是一个函数,可以使一个相同的调用或其它。


Here you can see a function in the same class that is defined as the start point.


这里你可以看到在同一个类中定义的起点函数。

using System;

using System.Threading;

namespace ThreadingTester

{

class ThreadClass

{

public static void trmain()

{

for(int x=0;x < 10;x++)

{

Thread.Sleep(1000);

Console.WriteLine(x);

}

}

static void <place w:st="on">Main</place>(string[] args)

{

Thread thrd1=new Thread(new ThreadStart(trmain));

thrd1.Start();

for(int x=0;x < 10;x++)

{

Thread.Sleep(900);

Console.WriteLine("Main :" + x);

}

}

}

}

Thread.Sleep(n) method puts the *this* thread into sleep for n milliseconds. You can see in this example, that in main we define a new thread, which its start point is the function trmain(), we then invoke the Start() method to begin the execution.


Thread.Sleep(n)方法把“this”线程置于n毫秒的休眠状态。你可以看看这个例子,在主函数我们定义了一个新的线程,其中它的起点是函数trmain(),我们然后包含了Start()方法开始执行。

If you run this example, you will know that the context switch between the threads (the process of letting a thread run in the CPU and then switching to another thread) lets the threads run almost together, I have placed the main thread to sleep 100 milliseconds less than the new thread in order to see which one thread runs "faster".


如果你运行这个例子,你就会了解线程间的切换(CPU从运行一个线程转到另一个线程)让线程几乎同时运行,为了能看哪个线程运行更快我把主线程设置比新线程少100毫秒。


Now, a thread could be assigned with a name, before Starting the thread we could:


现在,在开始线程前,先给线程命名:

Thread thrd1=new Thread(new ThreadStart(trmain));

thrd1.Name="thread1";

thrd1.Start();

In the thread itself, we can take the name into usage by:

Thread tr = Thread.CurrentThread;

Console.WriteLine(tr.Name);

After we made that, imagine that we don’t want the new thread to run to the end immediately when we start it, say we want to start the new thread, let it run, in a certain point the new thread will pause and will wait for a message from the main thread (or from another thread).

在完成上面程序后,设想我们不想在一开始新线程就让它马上运行结束,也就是说,我们开启了一个新线程,让它运行,在某个特定的时间点,新线程暂停并等待从主线程(或其他线程)发来的消息。


We can do that by defining:


我们可以这样定义:

public static ManualResetEvent mre = new ManualResetEvent(false);

The ManualResetEvent is being created with false as start state, this class is being used to signal another thread, and to wait for one or more threads. Note that all threads should have access to that class in order to signal or listen on the same one.

ManualResetEvent建立时是把false作为start的初始状态,这个类用于通知另一个线程,让它等待一个或多个线程。注意,为了通知或监听同一个线程,所有的其它线程都能访问那个类。


The waiting thread should:


等待线程这样写:

mre.WaitOne();

This will cause the waiting thread to pause indefinitely and wait for the class to be signaled.

这将引起等待线程无限期的阻塞并等待类来通知。


The signaling thread should:


发信号的线程应该这样:


mre.Set();

That will cause the class to be signaled as true, and the waiting thread will stop waiting. After signaling an event we can reset it to the base state by:

这样类就会被通知,值变成true,等待线程就会停止等待。在通知事件发生后,我们就可以使用下面语句把线程置于基状态:

mre.Reset();

Now lets implement all that in a single application:

现在让我们在程序执行一下:

using System;

using System.Threading;

namespace ThreadingTester

{

class ThreadClass

{

public static ManualResetEvent mre=new ManualResetEvent(false);

public static void trmain()

{

Thread tr = Thread.CurrentThread;

Console.WriteLine("thread: waiting for an event");

mre.WaitOne();

Console.WriteLine("thread: got an event");

for(int x=0;x < 10;x++)

{

Thread.Sleep(1000);

Console.WriteLine(tr.Name +": " + x);

}

}

static void <place w:st="on">Main</place>(string[] args)

{

Thread thrd1=new Thread(new ThreadStart(trmain));

thrd1.Name="thread1";

thrd1.Start();

for(int x=0;x < 10;x++)

{

Thread.Sleep(900);

Console.WriteLine("Main :" + x);

if(5==x) mre.Set();

}

while(thrd1.IsAlive)

{

Thread.Sleep(1000);

Console.WriteLine("Main: waiting for thread to stop...");

}

}

}

}

分享到:
评论

相关推荐

    C#数据同步源代码

    4. **多线程与并发**:在进行数据同步时,多线程和并发控制是必须考虑的。C#提供了`Thread`、`Task`、`Mutex`、`Semaphore`等工具来管理和协调并发访问,防止数据竞争和死锁。 5. **数据库事务**:在进行数据更改时...

    C#多线程解决界面卡死问题的完美解决方案

    在C#编程中,多线程技术是一种关键的性能优化手段,尤其对于处理耗时操作时,能够确保用户界面(UI)的响应性,避免出现界面卡死的现象。本解决方案将深入探讨如何利用C#的多线程特性来解决这个问题。 一、线程基础...

    C# 多线程查找文件

    在C#中,多线程是通过System.Threading命名空间中的类来实现的,尤其是Thread类。本篇文章将深入探讨如何使用C#进行多线程查找文件,并分析其背后的原理和实现细节。 首先,我们要理解C#中多线程的基本概念。一个...

    C#线程A中嵌套线程B做循环Demo

    总的来说,"C#线程A中嵌套线程B做循环Demo"展示了如何在C#中有效地实现线程间的嵌套和协作,以及如何处理循环执行中的线程同步问题。通过理解和掌握这些技术,开发者可以构建更加高效、健壮的多线程应用程序。

    C#线程、线程池和线程间同步的例子

    在这个"C#线程、线程池和线程间同步的例子"中,我们可以深入学习到如何在VS2008环境下创建和管理线程。 首先,线程是操作系统分配CPU时间的基本单元,每个进程至少包含一个线程。在C#中,我们可以通过`System....

    C# 多线程示例

    通过实际代码演示了如何在C# 中创建线程、管理线程之间的同步以及处理线程间通信等问题。 #### 描述:一个简单的C# 多线程例子,适合初学者学习 这个例子通过构建一个多线程程序来模拟生产者消费者模型,其中包含...

    C#同步异步操作说明

    在C#编程中,同步和异步操作是两种不同的执行方式,它们主要涉及到程序的执行流程和资源利用效率。同步方法和异步方法的核心区别在于处理任务的方式。 **同步方法**: 同步方法在调用后会阻塞主线程,直到方法执行...

    C#实现控制线程池最大数并发线程

    在C#编程中,线程池是用于管理线程资源的有效工具,它可以高效地调度线程,避免频繁创建和销毁线程带来的开销。在处理高并发任务时,合理控制线程池中的并发线程数量至关重要,以确保系统资源得到充分利用,同时避免...

    解析C#多线程编程中异步多线程的实现及线程池的使用

    5、线程同步与并发:、线程同步与并发:在多线程环境中,为了保证数据一致性,常常需要进行线程同步。C#提供了多种同步机制,如`Mutex`、`Semaphore`、`Monitor`、`lock`语句等。例如,使用`lock`关键字可以确保同一...

    跨线程访问控件实例.rar

    一种可能的实现方式是利用控件的SyncLock或Mutex机制,这是一种同步原语,可以确保同一时间只有一个线程能访问特定资源。另一种可能是利用事件或信号量(Semaphore)来协调线程,让后台线程等待直到UI线程完成更新后...

    ArrayList的线程安全测试

    在C#中,如果要在多线程中使用ArrayList,必须采取适当的同步措施,例如使用`lock`关键字、Monitor类或者`System.Collections.Concurrent`命名空间中的线程安全集合。 首先,让我们了解ArrayList的基本操作。...

    vb.net创建多线程

    本文将深入探讨如何利用`System.Threading.Thread`类在VB.NET中创建和管理多线程。 一、理解多线程 在单线程环境下,程序按顺序执行任务,而多线程则允许多个任务并行运行。每个线程代表程序中的一个独立执行路径。...

    线程笔记(多线程,异常)

    `Monitor`类提供`Enter()`和`Exit()`,相当于VB中的`SyncLock`或C#的`lock`关键字。`ReaderWriterLock`用于读写锁,`Mutex`和`AutoResetEvent`是事件同步工具,`Interlocked`类则提供了原子操作,如`i++`的线程安全...

    线程介绍(一)

    C#中的线程使代码能够并行执行,每个线程拥有独立的执行路径,能够在同一时间与其他线程一起运行。C#程序通常始于一个由CLR(Common Language Runtime)和操作系统创建的主线程。可以通过创建新的线程来扩展执行能力...

    c# 串口通讯如何多次重复发送一帧数据,并且保证发送和回复每一帧数据的顺序正

    在C#中进行串口通信时,确保数据的正确发送和接收是至关重要的。这个问题主要涉及两个关键点:一是如何多次重复发送同一帧数据并控制重试次数,二是如何保证发送多个数据包时不出现顺序混乱。 1. **多次重复发送一...

    多线程求和

    在C#中,可以使用`System.Threading.Thread`类来创建线程。以下是一个简单的示例: ```csharp Thread sumThread = new Thread(new ThreadStart(SumCalculator)); sumThread.Start(); ``` 在这里,`SumCalculator`是...

    Rust for C#/.NET 开发人员 中文 pdf

    - **Rust**:使用`std::thread`库进行多线程编程。 - **C#/.NET**:使用`System.Threading`命名空间进行多线程编程。 ##### 23. 生产者-消费者模型 - **Rust**:使用通道(`std::sync::mpsc::channel()`)实现生产者-...

    ASP技术常遇问题解答-如何防止Application对象在多线程访问中出现错误?.zip

    9. **测试与调试**:进行多线程测试,使用像`Thread.Sleep`这样的方法模拟高并发情况,以检查你的同步策略是否有效。 10. **性能优化**:虽然线程同步可以防止数据冲突,但过度的同步可能导致性能下降。因此,要...

    vbnet线程入门详解_跨线程调用窗体控件[收集].pdf

    4. `lock`关键字(C#中有,VB.NET中等价于`SyncLock`):用于在代码块级别同步线程,确保一次只有一个线程执行特定代码。 ### 六、线程池与异步编程 1. **线程池**:系统维护的一个线程集合,用于高效地重用线程,...

    线程安全调用

    - 在C#中使用`lock`关键字,在VB.NET中使用`SyncLock`。 - 注意使用`lock(typeof(X))`或`SyncLock(GetType(X))`来锁住类型对象时,同一类型下的所有实例将共享相同的锁,可能不是预期的行为。 - 使用`lock(this)`...

Global site tag (gtag.js) - Google Analytics