This program spawns a thread and the two threads communicate.It works fine and I would like to see how it appears in Windows Task Manager so I can understand it better. When I look in Task Manager I see this:
Should there be two entries somewhere in Task Manager because there are two threads? Is it all happening in .Net so there's nothing else to see in Task Manager?
using System;
using System.Threading;
namespace SensorNamespace {
class Sensor {
private ISensorInterface sensorInterface;
public Sensor(ISensorInterface sensorInterface) {
this.sensorInterface = sensorInterface;
}
private void ThreadStart() {
while (true) {
// The sensor reads a value from the real world and converts it to a double.
// We would need the unit of measure from the sensor manufacturer.
float value = (float)(new Random()).NextDouble();
sensorInterface.Update(value);
Thread.Sleep(500); // A nice pause because analog sensors are slow.
}
}
public void Start() {
Thread thread = new Thread(new ThreadStart(this.ThreadStart));
thread.Start();
}
}
}
using System;
using SensorNamespace;
using System.Threading;
namespace MultithreadedSensorInterfaceCSharp {
class Demo : SensorNamespace.ISensorInterface {
private static float sensorValue;
private static Sensor temperatureSensor;
static void Main(string[] args) {
Demo demo = new MultithreadedSensorInterfaceCSharp.Demo();
SensorNamespace.Sensor sensor = new SensorNamespace.Sensor(demo);
temperatureSensor = new SensorNamespace.Sensor(demo);
temperatureSensor.Start();
while (true) {
Console.WriteLine(sensorValue);
Thread.Sleep(5000);
}
}
void ISensorInterface.Update(float value) {
sensorValue = value;
}
}
}
namespace SensorNamespace {
interface ISensorInterface {
void Update(float value);
}
}
The entire project is here: https://github.com/nicomp42/MultithreadedSensorInterfaceCSharp
Related
By reading the documentation on msdn I was just trying to play around with some thread class functions. But found out this strange behavior there is no interrupt function in Thread Class. I am using Visual studio 2015 and .net core 1.0 console app
using System;
using System.Threading;
namespace ThreadingBasicsRight
{
public class Program
{
public static Object _lock = new Object();
public static void Main(string[] args)
{
Thread t = new Thread(test1);
t.Start();
t.Interrupt();
}
public static void test1()
{
lock (_lock)
{
for (int i = 0; i < 1000; i++)
{
Console.WriteLine(i);
}
Thread.Sleep(100);
}
}
public static void test2()
{
lock (_lock)
{
Console.WriteLine("process is not in a dead lock");
}
}
}
}
Hope you can help me with this one.i am beginner in multithreading programming with C#.
I am trying to build a program to write all numbers from range 1 to 2000 in two text files using two threads.
Every thread should write number from 1 to 2000 that not found at any of the two files "there is no duplicated numbers in the files" and every thread should't write the number that have been wrote by the another thread.
At the end if we merged the numbers of the two files we should have the numbers from 1 to 2000
Here is the source code i am trying but there is a problem in the writing for loop in the below image
i can't handle the process of writing by the two synchronized threads and i had exception:
Object synchronization method was called from an unsynchronized block of code.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
using System.Threading;
namespace Multithreading
{
class Program
{
static TextWriter file2 = new StreamWriter("file2 location");
static TextWriter file1 = new StreamWriter("file1 location");
static void Main(string[] args)
{
try
{
int[] array = new int[2000];
Thread thread1 = new Thread(Program.writeinfile1);
Thread thread2 = new Thread(Program.writeinfile2);
for (int counter = 1; counter <= 2000; counter++)
{
thread1.Start(counter);
thread2.Start(++counter);
Monitor.Enter(thread1);
Monitor.Wait(thread1);
Monitor.PulseAll(thread2);
}
}
catch (FileNotFoundException)
{
Console.WriteLine("the file you are trying to open is not found");
}
}
public static void writeinfile1(object x)
{
int converttointx = (int)x;
file1.WriteLine(converttointx);
file1.Close();
}
public static void writeinfile2(object y)
{
int converttointy = (int)y;
file2.WriteLine(converttointy);
file2.Close();
}
}
}
Here's an example of multi-threaded calls talking to one another to ensure they don't duplicate work.
I've not done exactly what you've asked for, since this looks quite homeworky; but hopefully this will help you to figure out the solution to your issue...
using System;
using System.Collections.Generic;
using System.Threading;
using System.Threading.Tasks;
namespace StackOverflow
{
class Program
{
static void Main(string[] args)
{
new Program();
Console.WriteLine("done");
Console.ReadKey();
}
Program()
{
int noThreads = 5;
int target = 2000;
StartThread(noThreads, target);
}
//kicks off our threads / waits for all threads to complete before returning
void StartThread(int noThreads, int target)
{
int id = noThreads--;
if (id > 0)
{
Doer doer = new Doer(id, target);
Thread t = new Thread(doer.Do);
t.Start();
StartThread(noThreads,target);
t.Join();
}
}
}
class Doer
{
static int marker = 0;
static readonly object syncLocker = new object();
readonly int id;
readonly int target;
public Doer(int id, int target)
{
this.id = id;
this.target = target;
}
public void Do()
{
while (marker < this.target)
{
int i;
lock (syncLocker)
{
i = ++marker;
}
System.Console.WriteLine("{0:00}: {1:###0}", id, i);
//Thread.Sleep(RandomNo()); //uncomment this & code below if your threads are taking turns / behaving too predictably
}
}
/*
static readonly Random rnd = new Random();
static readonly object rndSyncLocker = new object();
public static int RandomNo()
{
lock (rndSyncLocker)
{
return rnd.Next(0, 1000);
}
}
*/
}
}
You are not using the Monitor class correctly. The call to Monitor.PulseAll(thread2); should be called within thread the thread which owns the lock, which in this case would be within the writeinfile1 and writeinfile2 method.
This is why you are getting the exception:
Object synchronization method was called from an unsynchronized block of code.
See the following StackOverflow question for the correct way to use Monitor.PulseAll(object):
Help needed in Monitor.PulseAll()
I have a simple windows service written, here is its skeleton:
internal class ServiceModel {
private Thread workerThread;
private AutoResetEvent finishedEvent;
private Int32 timeout = 60000*15;
public void Start() {
this.workerThread = new Thread(this.Process);
this.finishedEvent = new AutoResetEvent(false);
this.workerThread.Start();
}
public void Stop() {
this.finishedEvent.Set();
this.workerThread.Join(30000);
}
public void Process() {
while(!this.finishedEvent.WaitOne(timeout)) {
// run things here
}
}
}
the first thing
The first thing that I can't understand is that service waits one timeout before running. Would rewriting the new AutoResetEvent(false); to new AutoResetEvent(true); cause a service to start without waiting?
the second thing
Due to some internal reasons (requesting data from external server/service, exception handling) sometimes it is not enough to wait that fixed 15..30-minutes timeout.
How do I rewrite it to work without a fixed timeout?
Do I need to remove that AutoResetEvent instance at all and run Process body inside an infinite loop?
public void Process() {
while(true) {
// run things here
}
}
edit. try-catch/lock
In Process method there is a global try-catch block:
public void Process() {
do {
try {
// processing goes here
}
catch(Exception ex) {
Logger.Log.Warn(ex); // or Log.Fatal(ex)...
}
}
while(true);
}
if I use a synchronization object where do I put the lock statement so that I'm able to call break when isStopped is true?
You don't have to deal with low-level thread and synchronization primitives API. Consider using Task Parallel Library (TPL). It's easy to implement OnStop using TPL cancellation framework:
using System.ServiceProcess;
using System.Threading;
using System.Threading.Tasks;
namespace WindowsService1
{
public partial class Service1 : ServiceBase
{
CancellationTokenSource _mainCts;
Task _mainTask;
public Service1()
{
InitializeComponent();
}
async Task MainTaskAsync(CancellationToken token)
{
while (true)
{
token.ThrowIfCancellationRequested();
// ...
await DoPollingAsync(token);
// ...
}
}
protected override void OnStart(string[] args)
{
_mainCts = new CancellationTokenSource();
_mainTask = MainTaskAsync(_mainCts.Token);
}
protected override void OnStop()
{
_mainCts.Cancel();
try
{
_mainTask.Wait();
}
catch
{
if (!_mainTask.IsCanceled)
throw;
}
}
}
}
Inside MainTaskAsync you can use Task.Run for any CPU-bound work items.
using Threads you can achieve your requirement using the following code:
internal class ServiceModel {
private Thread workerThread;
private object syncLock = new object();
private bool stop = false;
public void Start() {
this.workerThread = new Thread(this.Process);
this.workerThread.Start();
}
public void Stop() {
lock(syncLock) stop = true;
this.workerThread.Join(30000);
}
public void Process() {
while(true){
//your stuff here.
lock(syncLock)
{
if(stop)
break;
}
Thread.Sleep(30000);
}
}
}
When using the StartNew() method to kick off a process on a new thread, I need to figure out how to make another call into this object in that same thread (I assume this would be some sort of Join operation?).
The following example is dumbed down to illustrate the meat of what I am trying to do. I am well aware it is severely lacking in basic concurrency considerations. But I didn't want to cloud the code with all of that logic, so please forgive me on that.
The following console app shows what I am trying to accomplish. Assume on the StartNew() call a new thread with ID 9976 is created and the method invoked there. I would like the subsequent call to ProcessImmediate() in the file system watcher change event handler to be made on thread 9976 as well. As it stands, the call would share the same thread that is used for the file system watcher change event.
Can this be done, and if so, how?
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
var runner = new Runner();
runner.Run();
Console.ReadKey();
}
}
public class Runner
{
private Activity _activity = null;
private FileSystemWatcher _fileSystemWatcher;
public void Run()
{
_activity = new Activity();
// start activity on a new thread
Task.Factory.StartNew(() => _activity.Go());
_fileSystemWatcher = new FileSystemWatcher();
_fileSystemWatcher.Filter = "*.watcher";
_fileSystemWatcher.Path = "c:\temp";
_fileSystemWatcher.Changed += FileSystemWatcher_Changed;
_fileSystemWatcher.EnableRaisingEvents = true;
}
private void FileSystemWatcher_Changed(object sender, FileSystemEventArgs e)
{
// WANT TO CALL THIS FOR ACTIVITY RUNNING ON PREVIOUSLY CALLED THREAD
_activity.ProcessImmediate();
}
}
public class Activity
{
public void Go()
{
while (!Stop)
{
// for purposes of this example, magically assume that ProcessImmediate has not been called when this is called
DoSomethingInteresting();
System.Threading.Thread.Sleep(2000);
}
}
protected virtual void DoSomethingInteresting() { }
public void ProcessImmediate()
{
// for purposes of this example, assume that Go is magically in its sleep state when ProcessImmediate is called
DoSomethingInteresting();
}
public bool Stop { get; set; }
}
}
* UPDATE *
Thanks for the excellent responses. I took Mike's suggestion and implemented it for my console app. Below is the full working code which also includes the use of a cancellation token. I post this in case someone else might find it useful.
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
var runner = new Runner();
runner.Run();
Console.ReadKey();
runner.Stop();
Console.ReadKey();
}
}
public class Runner
{
private Activity _activity = null;
private FileSystemWatcher _fileSystemWatcher;
private CancellationTokenSource _cts = new CancellationTokenSource();
public void Stop() { _cts.Cancel(); }
public void Run()
{
_activity = new Activity();
// start activity on a new thread
var task = new Task(() => _activity.Go(_cts.Token), _cts.Token, TaskCreationOptions.LongRunning);
task.Start();
_fileSystemWatcher = new FileSystemWatcher();
_fileSystemWatcher.Filter = "*.watcher";
_fileSystemWatcher.Path = "C:\\Temp\\FileSystemWatcherPath";
_fileSystemWatcher.Changed += FileSystemWatcher_Changed;
_fileSystemWatcher.EnableRaisingEvents = true;
}
private void FileSystemWatcher_Changed(object sender, FileSystemEventArgs e)
{
// WANT TO CALL THIS FOR ACTIVITY RUNNING ON PREVIOUSLY CALLED THREAD
_activity.ProcessImmediate();
}
}
public class Activity : IDisposable
{
private AutoResetEvent _processing = new AutoResetEvent(false);
public void Go(CancellationToken ct)
{
Thread.CurrentThread.Name = "Go";
while (!ct.IsCancellationRequested)
{
// for purposes of this example, magically assume that ProcessImmediate has not been called when this is called
DoSomethingInteresting();
_processing.WaitOne(5000);
}
Console.WriteLine("Exiting");
}
protected virtual void DoSomethingInteresting()
{
Console.WriteLine(string.Format("Doing Something Interesting on thread {0}", Thread.CurrentThread.ManagedThreadId));
}
public void ProcessImmediate()
{
// for purposes of this example, assume that Go is magically in its sleep state when ProcessImmediate is called
_processing.Set();
}
public void Dispose()
{
if (_processing != null)
{
_processing.Dispose();
_processing = null;
}
}
}
}
First, you should use TaskCreationOptions.LongRunning if you are creating a task that will not complete quickly. Second, use an AutoResetEvent to signal the waiting thread to wake up. Note that below ProcessImmediate will return before DoSomethingInteresting has completed running on the other thread. Example:
using System.Threading;
public class Activity : IDisposable
{
private AutoResetEvent _processing = new AutoResetEvent(false);
public void Go()
{
while (!Stop)
{
// for purposes of this example, magically assume that ProcessImmediate has not been called when this is called
DoSomethingInteresting();
_processing.WaitOne(2000);
}
}
protected virtual void DoSomethingInteresting() { }
public void ProcessImmediate()
{
_processing.Set();
}
public bool Stop { get; set; }
public void Dispose()
{
if (_processing != null)
{
_processing.Dispose();
_processing = null;
}
}
}
User mike has given a better solution, which will be appropriate when you like to call the same method immediately. If you want to call a different methods immediately I'll expand mike's answer to achieve that.
using System.Threading;
public class Activity : IDisposable
{
private AutoResetEvent _processing = new AutoResetEvent(false);
private ConcurrentQueue<Action> actionsToProcess = new ConcurrentQueue<Action>();
public void Go()
{
while (!Stop)
{
// for purposes of this example, magically assume that ProcessImmediate has not been called when this is called
DoSomethingInteresting();
_processing.WaitOne(2000);
while(!actionsToProcess.IsEmpty)
{
Action action;
if(actionsToProcess.TryDeque(out action))
action();
}
}
}
protected virtual void DoSomethingInteresting() { }
public void ProcessImmediate(Action action)
{
actionsToProcess.Enqueue(action);
_processing.Set();
}
public bool Stop { get; set; }
public void Dispose()
{
if (_processing != null)
{
_processing.Dispose();
_processing = null;
}
}
}
To execute different methods on the same thread you can use a message loop that dispatches incoming requests. A simple option would be to use the event loop scheduler of the Reactive Extensions and to "recursively" schedule your Go() function - if in the mean time a different operation is scheduled it would be processed before the next Go() operation.
Here is a sample:
class Loop
: IDisposable
{
IScheduler scheduler = new EventLoopScheduler();
MultipleAssignmentDisposable stopper = new MultipleAssignmentDisposable();
public Loop()
{
Next();
}
void Next()
{
if (!stopper.IsDisposed)
stopper.Disposable = scheduler.Schedule(Handler);
}
void Handler()
{
Thread.Sleep(1000);
Console.WriteLine("Handler: {0}", Thread.CurrentThread.ManagedThreadId);
Next();
}
public void Notify()
{
scheduler.Schedule(() =>
{
Console.WriteLine("Notify: {0}", Thread.CurrentThread.ManagedThreadId);
});
}
public void Dispose()
{
stopper.Dispose();
}
}
static void Main(string[] args)
{
using (var l = new Loop())
{
Console.WriteLine("Press 'q' to quit.");
while (Console.ReadKey().Key != ConsoleKey.Q)
l.Notify();
}
}
Simple as this! This is my attempt at one, which requires that functions to be threaded with it use a Pause() function through itself in pausable sections.
using System;
using System.Threading;
class BlackThread {
private bool paused;
private Thread innerThr;
// ---
public bool IsAlive {
get {
return innerThr.IsAlive;
}
}
// ===
public void SetAndGo (ThreadStart start) {
paused = false;
innerThr = new Thread(start);
innerThr.Start();
WaitForIt();
}
// ---
public void Pause() {
paused = true;
while (paused);
}
public void Unpause() {
paused = false;
}
public void WaitForIt() {
while(!paused && IsAlive);
}
public void Continue() {
Unpause();
WaitForIt();
}
}
class MainClass {
static void pausableFunction (BlackThread self) {
Console.WriteLine("* Waiting...");
self.Pause();
Console.WriteLine("* Doing stuff.");
self.Pause();
Console.WriteLine("* Finished!");
}
static void Main() {
BlackThread noir = new BlackThread();
noir.SetAndGo(() => pausableFunction(noir));
while (noir.IsAlive) {
Console.Write("> ");
Console.ReadKey();
noir.Continue();
}
}
}
Sadly, it's not one that can be paused at any time, but a thread for functions that require to wait for outside processing to be able to continue. Like an action by a game mob that requires its frame to be drawn by the draw loop before it can continue, and the mob's A.I.'s is processed in the game's main loop.
I guess it'd make it some kind of pseudo-thread? Anyway.
It would allow the mob to process this action bit by bit every loop, instead of cascading checkings in its A.I. like...
if mob is doing action {
if mob has already done this previous part of the action {
do the following part
}
}
...it'd rather be like this, in a thread:
do the first step of the action
Wait for it to be rendered...
do the following step of the action
Wait for it to be rendered...
do the last step of the action
(Action ends here, no need to wait for anything anymore)
Now, my implementation has a bug which I cannot figure out how to fix. When it's supposed to unpause the BlackThread, it remains paused in the function (in this case, pausableFunction()) that uses it. I guess it's because of how the instance is passed?
If it's what I'm guessing - that is, something (and I'd guess it's bool paused) is passed by value instead of reference - how could I fix it?
I'm really used to the pointers of C and C++, so sometimes I get a bit tangled when dealing in C# with the communication of an object's values between scopes.
This here is a version of the code the works, a prototype to say:
using System;
using System.Threading;
class Program {
static bool paused;
static void Pause() {
paused = true;
while (paused);
}
static void Unpause() {
paused = false;
}
static void WaitForIt(Thread waited) {
while(!paused && waited.IsAlive);
}
static void Continue (Thread ToStop) {
Unpause();
WaitForIt(ToStop);
}
static void SetAndGo (out Thread thread, ThreadStart Start) {
thread = new Thread(Start);
thread.Start();
WaitForIt(thread);
}
// ---
static void thr (string chant) {
// Console.WriteLine("Waiting...");
// Pause();
// Console.WriteLine("{0}", chant);
// Pause();
// Console.WriteLine("Well, I'm finished!");
Console.WriteLine("I'm finished!");
}
static void Main() {
// Thread tt = new Thread(() => thr());
// tt.Start();
// WaitForIt(tt);
Thread tt;
SetAndGo(out tt, (() => thr("I'm doing stuff.")));
while (tt.IsAlive) {
Console.Write("> ");
Console.ReadKey();
Continue(tt);
}
}
}
I'm only not using it because I'd rather have everything in charge of a specific class for the matter, something that would also enhance readability.
Alright, I've accomplished what I was trying already, so I'll leave my code here for future reference!
This is the BlackThread class in the end:
using System;
using System.Threading;
class BlackThread {
//* ===== *//
private AutoResetEvent pauser = new AutoResetEvent(false);
private AutoResetEvent waiter = new AutoResetEvent(false);
private Thread innerThr;
// ----- //
public bool IsActing {
get {
if (innerThr != null) return innerThr.IsAlive;
else return false;
}
}
//* ===== *//
public void KickStart_(ThreadStart start) {
innerThr = new Thread(start);
innerThr.Start();
WaitForIt();
}
// ----- //
// FOR THE THREADED FUNCTION
public void Wait() {
waiter.Set();
pauser.WaitOne();
}
public void End() {
waiter.Set();
}
// ----- //
// FOR BLACKTHREAD MANAGING
private void WaitForIt() {
waiter.WaitOne();
}
public void Continue() {
if (IsActing) {
pauser.Set();
WaitForIt();
}
}
//* ===== *//
}
And here, an example of its use:
class MainClass {
static void pausableFunction() {
Console.WriteLine("* Waiting...");
Event.Wait();
Console.WriteLine("* Doing stuff.");
Thread.Sleep(1000);
Event.Wait();
Console.WriteLine("* Finished!");
Event.End();
}
static void anotherFunction(int foo) {
Console.WriteLine("* Wanna know the value of a number?");
Event.Wait();
Console.WriteLine("* I'll tell you. It's {0}!", foo);
Event.End();
}
static void simpleFunction() {
Console.WriteLine("* I'm done already!");
}
static BlackThread Event = new BlackThread();
static Random Rand = new Random();
static void Main() {
int r;
do {
if (!Event.IsActing) {
Console.WriteLine();
r = Rand.Next(3);
if (r == 0) {
Event.KickStart_(() => pausableFunction());
}
else if (r == 1) {
simpleFunction();
}
else {
Event.KickStart_(() => anotherFunction(Rand.Next(20) + 1));
}
}
else {
Event.Continue();
}
Console.Write("> ");
Console.ReadKey();
} while(true);
}
}
What I've opted to use in the end were two AutoResetEvent handlers. One is managed in the function of the thread that requires pausing, and that pauses the main loop, the waiter ARE, and another, the pauser ARE, managed in the main loop, and that pauses the thread with the function with support for BlackThread; that is, has acess to a BlackThread instance.
In this case I've used a static BlackThread object, but it can also be passed as a parameter to the function.
And yes, it's named after the Buddhist hell!