I am making a program for a robot in a competition, and need to multithread.
When I make a second task (task two()) and try to start (startTask) it with a button press from a controller, it just executes the first statement of the task and only as long as the button is pressed, instead of the whole block. I've tried many things including putting a loop in the second task also, using a function instead of a task and sleeping for 200 milliseconds before, and after the startTask(two); function, but the same thing happens every time.
I can't post my program because I don't want other people to steal it, sorry.
What edits will make it run the whole block?
Any help would be appreciated.
Since this is Controller Mode, I'm assuming that you are setting the motors to stop when the corresponding button is not pressed.
if([...])
[...]
else
{
setMotorSpeed(motor10, 0);
}
This is the cause for the stopping of the motors when you release. All of the other methods that you tried had nothing to do with this, so they shouldn't have worked.
You need to put something like this:
int Motor10Speed;
[...]
if([...])
[...]
else
{
setMotorSpeed(motor10, Motor10Speed);
}
This will control an individual motor. Repeat this for all other motors being used.
After that is done, make the function look something like this:
task mini_function();
task main()
{
[...]
}
task mini_function()
{
Motor10Speed = 50;
sleep(1000);
Motor10Speed = 0;
}
Expand the above program so it matches your current function, while using the MotorSpeed variables as setMotorSpeed variables.
This should make you able to drive and run a function at the same time without them interrupting each other.
Related
In my onDisbale() method in my Main class I have a loop which creates and starts new BukkitRunnables.
I'm getting a error in console: org.bukkit.plugin.IllegalPluginAccessException: Plugin attempted to register task while disabled I need to somehow wait in my onDisable() method until all the BukkitRunnables I create in the loop are finished. How to do that?
My code looks like this:
#Override
public void onDisable() {
for (Player p : Bukkit.getOnlinePlayers()) {
new PlayerDataSaverRunnable().runTaskAsynchronously(this);
}
}
The onDisable method is the very last thing that gets called before your plugin is disabled and the server shuts down. So, as the error message says, you unfortunately can't schedule any new tasks in the onDisable function.
You mentioned in a comment that you were trying to write to a file in the plugins folder, and under normal circumstances you'd want to do that asynchronously. But, because onDisable only ever gets called when the server is shut down (or when the entire server is reloaded with /reload), it's perfectly fine to run code here that blocks the main thread and could potentially take a few seconds to run — in the case of a shutdown, by the time this method gets called, all the players will have already been kicked off the server, and so there's no "lag" to complain about. If your plugin is super advanced and has to save a bunch of stuff, I don't think any server owners would complain even if it took 10 or so seconds to disable.
Of course, you would have to be saving something crazy for it to take a whole 10 seconds to save. More than likely, most files will save in just a few milliseconds.
If you're really dead-set on disabling the plugin as fast as possible, you might consider having some async task that runs every 5 minutes or so and auto-saves the files. Then, in onDisable, you could only save files that changed since the auto-saver was last run. That's a good practice anyways, just incase the server crashes or the power goes out and the onDisable method doesn't get a chance to run. But, then again, I would still recommend that you save everything in the onDisable method (that's what I do for all of my plugins, as well), even if it will take a few seconds and block the main thread, just so you can be 100% sure that everything gets saved correctly.
I need to write a script, that takes an array of values and multithreaded way it (forks?) runs another script with a value from array as a param, but so max running forks would be set, so it would wait for script to finish if there are more than n running already. How do I do that?
There is a plugin named child_process, but not sure how to get it done, as it always waits for child termination.
Basically, in PHP it would be something like this (wrote it from head, may contain some syntax errors):
<php
declare(ticks = 1);
$data = file('data.txt');
$max=20;
$child=0;
function sig_handler($signo) {
global $child;
switch ($signo) {
case SIGCHLD:
$child -= 1;
}
}
pcntl_signal(SIGCHLD, "sig_handler");
foreach($data as $dataline){
$dataline = trim($dataline);
while($child >= $max){
sleep(1);
}
$child++;
$pid=pcntl_fork();
if($pid){
// SOMETHING WENT WRONG? NEVER HAPPENS!
}else{
exec("php processdata.php \"$dataline\"");
exit;
}//fork
}
while($child != 0){
sleep(1);
}
?>
After the conversation in the comments, here's how to have Node executing your PHP script.
Since you're calling an external command, there's no need to create a new thread. The Node.js runloop understands that calls to external commands are async operations, and it can execute all of them at the same time.
You can see different ways for executing an external process in this SO question (linked answer may be the best in your case).
However, since you're already moving everything to Node, you may even consider rewriting your "process.php" script to Node.js code. Since, as you explained, that script connects to remote servers and databases and uses nslookup (which you may not really need with Node.js), you won't need any separate thread: they're all async operations that Node.js excels at performing.
I am making a simulation tool, that runs simulation (in a separate thread) over user defined number of iterations, which can be entered in an Edit control on the Ribbon Bar. I would like to reuse it to show current iteration during simulation. I also also put CMFCRibbonProgressBar to show the progress. The Ribbon Bar is created with resource editor.
The question is what is the what to get the progress bar and iteration counter to get timely updated without causing the GUI to become unresponsive?
The conventional way over ON_UPDATE_COMMAND_UI routines requires activity in the window, like moving the mouse.
So I probably need a thread that would update this controls. Things like simply creating a thread and trying to update the controls from or using concurrency::parallel_invoke are not suitable.The former simply doesn't work, the latter works, but causes GUI to freeze.
I store pointers in my document to simplify access to the controls. https://stackoverflow.com/a/25429446?noredirect=1
My general idea is (pseudocode)
beginUpdatingThread()
{
while(simulating)
{
updateEditControl();
updateProgressBar();
sleep_40_ms();//conserves the resorces as there is no sense to update more frequent than 25 times per second
}
}
What is correct way of implementing this?
ASSERT(m_hWnd!=NULL);
MSG msg;
while (simulating)
{
// Handle dialog messages
while(PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
{
if(!IsDialogMessage(&msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
}
I solved this by adding a method to the main window that performs the update. now the thread updating from above continually post messages to the main window to perform the update:
auto h = static_cast<CMainFrame*>(AfxGetMainWnd())->m_hWnd;
//here code for starting simulation in a separate thread
std::thread updating([this,h]{
while (simulating)
{
::PostMessage(h, WM_UPDATE_VISUALS, sumulator.getCurrentIteration(), 0);
std::this_thread::sleep_for(std::chrono::milliseconds(40));
}
::PostMessage(h, WM_UPDATE_VISUALS, num_iterations, 0);
});
updating.detach()
I made a subtle mistake at first by capturing h by reference, which quickly expires
But in the end, the above code does exactly what I wanted to achieve
I want to load a new URL (which is in a array), everytime I press the button. I have the following code to do so:
public function selectRadio(radio:Radio):void {
var soundR:Sound = new Sound();
if(!playing) {
soundR.load(new URLRequest(radio.getURL()));
soundChannel = soundR.play();
playing = true;
}
else{
soundChannel.stop();
playing = false;
}
trace("You are now listening to " + radio.getTitle());
}
But it gives me this error:
"implicit coercion of a value of type flash.net:URLRequest to an unrelated type string"
It works if I just leave it like this:
soundR.load(radio.getURL());
But if i do so, I can only press play and stop 4 times. After the fourth there is no sound, like it can't load the URL.
Is it possible to fix this?
Radio.getURL() should return a string instead of a URLRequest?
Ah nevermind I see you tried avoiding that by removing URLRequest, but you are having problems with only 4 connections.
In all but the simplest cases, your application should pay attention to the sound’s loading progress and watch for errors during loading. For example, if the click sound is fairly large, it might not be completely loaded by the time the user clicks the button that triggers the sound. Trying to play an unloaded sound could cause a run-time error. It’s safer to wait for the sound to load completely before letting users take actions that might start sounds playing.
http://help.adobe.com/en_US/as3/dev/WS5b3ccc516d4fbf351e63e3d118a9b90204-7d25.html
If you can't wait for the sound to completely load you may need NetStream:
http://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/net/NetStream.html
I need help how to unfreeze my dialog box. I'm using MFC and I have an infinite loop I want to execute when a button is pressed. However, the dialog box freezes when the infinite loop starts. Now I looked at this thread where someone was having a similar problem.
Unfortunately I tried multithreading but I found out that It can't work for me because I'm using an api that uses OLE automation and I'm getting an unhandled memory exception. I think this is because program uses the serial port and i read somewhere you can only use the handle to the serial port in one thread.
My program is simply to see if someone has dialed in to my modem and wait for them to send me a file, then hangup. Here is my loop.
while(1)
{
//get rid of input buffer
ts->_this->m_pHAScript->haReleaseRemoteInput();
ts-> _this->textBox->SetWindowTextA("thread Commence");
//wait for connected
if(success = ts->_this->m_pHAScript->haWaitForString("CONNECT",timeout))
{
//getFile
if(success = ts->_this->m_pHAScript->haWaitForXfer(5000))
{
//hangup
ts->_this->haTypeText("+++ath\r");
}
}
}
Is there a way to unfreeze the dialog box?
Add this code inside while loop:
MSG msg;
while(PeekMessage(&msg, GetSafeHwnd(), 0, 0, PM_REMOVE))
{
DispatchMessage(&msg);
}
The GUI in Windows relies on a message loop - somewhere in your code, either explicitly or hidden in a framework, there's a loop that checks for a message in a queue and processes it. If anything blocks the code from returning to that loop, the GUI gets frozen.
There are a few ways around this. One was given by David Brabant, essentially duplicating the loop. Another is to start a new "worker" thread that runs the blocking operation independently. If your message loop has a function that it calls when it is idle, i.e. no more messages are in the queue, you can do some processing there; that's not possible in your example however.