Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 8 years ago.
Improve this question
I have an ASP.NET app, where a single request invokes 6 very slow methods. The methods are not async and I don't have the time to rewrite and test them. How can I run those 6 methods on 6 threads and then agregate the results? I'm on .NET 4.5.
You can simply use Task.Run to create a task that runs each of the methods in another thread, and then wait for them all to finish so that you can use the results.
var tasks = new Task<YourResultType>[]
{
Task.Run(() => Method1()),
Task.Run(() => Method2()),
Task.Run(() => Method3()),
Task.Run(() => Method4()),
Task.Run(() => Method5()),
Task.Run(() => Method6()),
};
var results = Task.WhenAll(tasks).Result;
If the methods don't all have results of the same type, allowing you to put all of the tasks into an array, then you'll need to have separate local variables for each task and use Result on each one after starting them all.
Related
Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 2 years ago.
Improve this question
I am creating a bot for a website where the system logs in with several accounts and does a certain action the problem is when it is time to repeat the process example I have 10 accounts and I would like all accounts to do the same process as the first, the accounts are browned in a txt file. What is the correct way to do this?
Sometimes the function runs ahead of time, I'm new to C # I'm studying
My code looping :/
Task.Delay(2000).ContinueWith(t => setMail());
Task.Delay(3500).ContinueWith(t => nextButton());
Task.Delay(5000).ContinueWith(t => setPass());
Task.Delay(6500).ContinueWith(t => logionButton());
Task.Delay(7500).ContinueWith(t => SucessLogin());
You are creating 5 independent tasks which will all run together, rather than one after the other. Instead, just collapse them to one async/await function:
async Task TestStuff(Account account)
{
await Task.Delay(2000);
setMail();
await Task.Delay(3500);
nextButton();
await Task.Delay(5000);
setPass();
await Task.Delay(6500)
logionButton();
await Task.Delay(7500);
SucessLogin();
}
You mentioned that you've got accounts stored in a file. In this example you'll need to create an Account class and populate it with the information you get from the file. For example:
List<Account> accounts = LoadAccounts("some-file.txt")
foreach(var account in accounts)
{
await TestStuff(account);
}
Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 6 years ago.
Improve this question
I was making a game on C# just for practice and learning (first program in C#) and I wondered if it was possible for C# to let me, while my program (the game) is running to simultaneously run another piece of code that would be the background music (just some Console.Beep() basic stuff).
In short, my question is if it would be possible for both the code for the background music and the one for the game to be in the same program, and if not, if there is an easy way to make it in just one console.
There are many options for threading. One of the most simpler are just using Task()
// Here I store the token for future use
processMe = new MyBackgroundProcess(ERPManager.CancellationTS.Token);
var aTask = new Task(() =>
{ // Everything here runs on another thread
processMe.Run();
}, ERPManager.CancellationTS.Token);
In this case, the "Run" method will run on a separte thread.
The "Token" is for cancelling the task. "processMe" stores the reference and asks "I am cancelled?"
For example, let's say Run() is like
public void Run()
{
while (! token.IsCancellationRequested)
{
PlayMusicSlice();
}
}
So you check if it's cancelled. When you finish, you just do a
ERPManager.CancellationTS.Cancel()
On your main thread.
You can play with things like
List<Task> tasks = new List<Task> ();
tasks.Add(new Task(() => Process1.Run(), aCancellationToken));
tasks.Add(new Task(() => Process2.Run(), aCancellationToken));
tasks.Add(new Task(() => Process3.Run(), aCancellationToken));
And then do
Task.WaitAll(tasks.ToArray());
Or
Task.WaitAny(tasks.ToArray());
And then query the status
if (tasks[0].IsCompleted()) { ... }
if (tasks[0].IsFaulted()) { ... }
You will face a lot of issues like concurrency and problems accessing UI elements, but this is a good start :)
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 7 years ago.
Improve this question
Hi I have code like below in a for loop. It is in a for loop because the number of times it needs to be run can vary dependent on how many items the user has added.
var taskList = new List<Task<IEnumerable<MyObject>>>();
for (int i = 0; i < numOfBatches; i++)
{
var task = Task.Factory.StartNew(() => MyMethod(variableA, variableB));
taskList.Add(task);
}
//Wait for all the tasks to complete
Task.WaitAll(taskList.Cast<Task>().ToArray());
return taskList.SelectMany(x => x.Result);
Is there a better way I can run these tasks in Parallel? I was thinking about a parallel for each loop but because the number of iterations of the loops isn't fixed I don't think I can use a parallel for each
There isn't necessarily a problem with the code. However if I have 10,000 items inputted it takes about 18 minutes and I was thinking if I could run the Tasks in parallel it may return faster. If 10,000 items are inputted the number of batches will be 10,000/25 = 400
The actuall code in MyMethod calls a 3rd party external service to return data based on data entered by user
Processing a list in parallel is about the easiest of parallel algorithms there is:
ParallelEnumerable.Range(0, numOfBatches)
.Select(_ => MyMethod(variableA, variableB))
.ToList();
It is a code smell to create unbounded numbers of tasks because this can lead to resource exhaustion and the code is clumsy.
Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 8 years ago.
Improve this question
private async void btnLoadFile_Click(object sender, EventArgs e)
{
if(AccountsFile.ShowDialog()==DialogResult.OK)
{
Accounts = File.ReadAllLines(AccountsFile.FileName);
foreach(string str in Accounts)
{
await LoadAccount(str);
}
}
}
I've ran into a problem, I know how Asynchronous programming works it will wait for the task to be complete but LoadAccount() will never complete because it calls a function with a never ending while loop so it will not reach the next string in Accounts.
I don't know where to start with this problem. Any solutions?
Instead of waiting for each account successively, you could wait for them collectively. This way, even if one of your accounts enters an infinite loop, the others could still proceed to load.
Accounts = File.ReadAllLines(AccountsFile.FileName);
Task completionTask = Task.WhenAll(Accounts.Select(LoadAccount));
You would typically want to store completionTask in a class variable. Subsequently, when you break out of the indefinite while loop within your LoadAccount calls (for example, by signalling cancellation via a polled CancellationToken), you can use this completionTask to wait for all your tasks to complete.
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 9 years ago.
Improve this question
I've got an activity that I need to run on a background thread in a C#/XAML app, so I'm doing this:
Task.Factory.StartNew(() => ImportFile());
I'm returning the Task value to another bit of code that then needs to take action after the thread-based work has completed. The code looks like this:
Action<Task> finalise = async delegate { await FinishImport(dbList); };
dbList.ImportFileAsync().ContinueWith(finalise);
When I run the code, however, debugging statements in FinishImport are being executed before the background thread has finished.
What am I misunderstanding here? I thought the whole point of ContinueWith was that it would execute the continuation code after the target task completes.
You should use Task.Run rather than Task.Factory.StartNew in async code. Task.Run understands async methods while StartNew will return a Task representing only the beginning of that async method.
As a side note, it's usually best to not have Task.Run hidden inside a library method.
Also, it's far easier to use await than ContinueWith. And async methods should end with "Async".
So, applying these guidelines makes your code look like:
await Task.Run(() => dbList.ImportFileAsync());
await FinishImportAsync(dbList);
what ImportFileAsync() does?
finalise will run after the thread of ImportFileAsync() will end
if
ImportFileAsync(){ Task.Factory.StartNew(() => ImportFile());}
then ImportFileAsync will call a new thread for ImportFile() and then exit it won't wait for ImportFile()
to finish
you wanna do
Task.Factory.StartNew(() => dbList.ImportFile()).ContinueWith(finalise);