I'm trying to make threads using C++'s standard library via functions.
#include <iostream>
#include <thread>
using namespace std;
void print()
{
printf("PRINT\n");
printf("PRINT2\n");
}
void createThread()
{
thread newThread(print);
}
int main()
{
createThread();
cin.get();
}
the program compiles and runs but once the thread is finished it creates a "debug error". Any thoughts?
The problem is that your thread object goes out of scope before you call its detach() or join() member.
Try this:
int main()
{
thread newThread(print);
...
newThread.join();
return 0;
}
If your "debug error" means the compiler error message, you should check if -pthread flag is set. That is compile the code with
$ g++ -std=c++11 main.cpp -pthread -o main
If your "debug error" means the runtime error, you should remember to join() after you create a thread.
source code:
#include <iostream>
#include <thread>
void print()
{
std::cout << "PRINT" << std::endl;;
std::cout << "PRINT 2" << std::endl;;
}
void create_thread()
{
std::thread print_thread(print);
print_thread.join(); // remember to join()
}
int main()
{
create_thread();
return 0;
}
In addition, you may pay attention to 4 additional points:
using namespace std is not recommended.
remember to join() after you create a thread
return 0 for main()
printf() is in stdio.h. use std::cout for iostream
Related
I am new to threads, I am trying to simulate the critical section race condition problem in this code.
#include <iostream>
#include <thread>
#include <chrono>
using namespace std;
using namespace std::chrono;
int x = 20;
void increment()
{
++x;
}
void decrement()
{
--x;
}
int main()
{
thread t1(increment);
thread t2(decrement);
cout << x;
return 0;
}
But, this code terminates with SIGABRT.
terminate called without an active exception
21
Why I am getting SIGABRT in this code?
You must call join for the threads so that they are properly terminated
t1.join();
t2.join();
I have a small solution in visual studio 2012. The solution consists of two projects (Scanner and TestApp), Scanner is a dll and TestApp is a small application using the dll.
I would like a function in the dll to run in a thread and to report its result back via a queue to the TestApp.
To test this I wrote a minimal application, but depending on how I launch the thread I get different results and I would like to understand why.
The Scanner.h file looks like this:
#pragma once
#include <iostream>
#include <string>
#include <stdint.h>
#include <atomic>
#include <future>
#include <thread>
#include "version.h"
#include "threadsafe_queue.h"
#include "capture_data.h"
#include "process_data.h"
#ifdef SCANNER_EXPORTS
#define SCANNER_API __declspec(dllexport)
#else
#define SCANNER_API __declspec(dllimport)
#endif
class Scanner
{
public:
static SCANNER_API void run();
static SCANNER_API void stop();
};
Scanner.cpp:
#include "stdafx.h"
#include "Scanner.h"
std::vector<std::future<int>> my_futures;
void Scanner::run()
{
CaptureData capture_data(1234);
auto t = std::async(std::launch::async, &CaptureData::get_data, capture_data);
my_futures.push_back(std::move(t));
}
void Scanner::stop()
{
for(int n=0; n<my_futures.size(); n++) {
auto e = std::move(my_futures.back());
e.get();
my_futures.pop_back();
}
}
The class CaptureData is defined in capture_data.h and capture_data.cpp.
capture_data.h:
#pragma once
#include <atomic>
#include <thread>
#include "iq_data.h"
#include "threadsafe_queue.h"
class CaptureData
{
public:
CaptureData(double freq_start);
void configure();
void get_data();
private:
double m_test;
};
capture_data.cpp
#include "stdafx.h"
#include "capture_data.h"
#include "Scanner.h"
ThreadsafeQueue<int> g_queue_1;
SCANNER_API ThreadsafeQueue<int> g_queue_2;
CaptureData::CaptureData(double test)
: m_test(test) {}
void CaptureData::get_data()
{
cout << "1: " << m_test << std::endl;
Sleep(5000);
cout << "2: " << m_test << std::endl;
g_queue_2.push(3);
cout << "Capture has now pushed data" << std::endl;
}
And finally the TestApp.cpp:
#include "stdafx.h"
#include "tchar.h"
#include <stdint.h>
#include <string>
#include "Scanner.h"
SCANNER_API extern ThreadsafeQueue<int> g_queue_2;
int _tmain(int argc, _TCHAR* argv[])
{
Scanner scanner;
scanner.run();
cout << "TestApp waiting for data..." << std::endl;
int data;
g_queue_2.wait_and_pop(data);
cout << "TestApp got data: " << data << std::endl;
scanner.stop();
return 0;
}
In Scanner.cpp I have tried to launch the thread in two different ways, the first way:
auto t = std::async(std::launch::async, &CaptureData::get_data, capture_data);
Second way is with a reference to the object "capture_data":
auto t = std::async(std::launch::async, &CaptureData::get_data, &capture_data);
The first way seems to work as I intended the application to work and I get the following printouts in my terminal:
TestApp waiting for data...
1: 1234
2: 1234
Capture has now pushed data
TestApp got data: 3
Press any key to continue...
If I use the second way I get:
TestApp waiting for data...
1: 6.95166e-310
2: 6.95166e-310
Capture has now pushed data
TestApp got data: 3
Press any key to continue...
So, what I do not understand is why the variable "m_test" get messed up in the second case.
I would very much appreciate if anyone could shed a light on this.
/M
In the following code:
void Scanner::run()
{
CaptureData capture_data(1234);
auto t = std::async(std::launch::async, &CaptureData::get_data, capture_data);
my_futures.push_back(std::move(t));
}
capture_data is a local variable that goes out of scope and gets destroyed when the function returns. If you pass a pointer to that variable into async that pointer becomes a dangling pointer causing undefined behaviour. That does not happen if you pass it by value, as you do in the above snippet.
You are trying to pass a pointer to a stack allocated object. This object is destructed at the end of the Scanner::run() method. Thus, the pointer is now pointing to invalid memory when the async function runs.
The first method works, because the capture_data variable is move constructed when it is passed to the function, therefore it still retains it's structure.
I recommend using lambda functions than passing the raw member function:
void Scanner::run()
{
CaptureData capture_data(1234);
auto t = std::async(std::launch::async, [capture=std::move(capture_data)]() { capture.get_data(); });
my_futures.emplace_back(t);
}
Even better is to construct the object inside the lambda function:
void Scanner::run()
{
auto t = std::async(std::launch::async, []() {
CaptureData capture_data(1234);
capture_data.get_data();
});
my_futures.emplace_back(t);
}
I am studying about threads in C++11 now, and I met the following line of code:
lock_guard<mutex> lg(mutex);
There is no variable mutex. mutex is only name of type.
Can anyone explain me how above line of code works?
Why compiler(GCC) doesn't print any error?
Complete code:
#include <iostream>
#include <thread>
#include <mutex>
#include <chrono>
using namespace std;
void do_something()
{
lock_guard<mutex> lg(mutex);
cout << "Working..." << endl;
this_thread::sleep_for(chrono::milliseconds(3000));
}
int main()
{
thread thd(do_something);
thd.join();
}
The compiler thinks this is a prototype function declaration:
lock_guard<mutex> lg(mutex);
To be clear, the compiler parses this as the declaration of a function named 'lg' which takes a mutex as a parameter and returns a lock_guard instance.
#include <mutex>
int main()
{
using namespace std;
lock_guard<mutex> lg(mutex);
return 0;
}
vc12 output : warning C4930 : 'std::lock_guard<std::mutex> lg(std::mutex)' : prototyped function not called(was a variable definition intended ? )
In C++ structure, class, enumeration and union names are in their own namespace (not a C++ namespace), which allows you to have variables with the same name as a structure.
For example:
struct SomeStruct
{
// Member...
};
SomeStruct SomeStruct; // Valid declaration
As for you not getting an error, if the function you use the shown it in a member function, then it could be that the class has a member variable with the name mutex.
I am really new in C++, and I can not solve the compilation error below.
data_structure.h
#include <stdint.h>
#include <list>
namespace A {
class B {
public:
bool func_init(); // init
};
};
data_structure.cpp
#include "data_structure.h"
using namespace A;
bool B::func_init(){
std::cout << "test init" << std::endl;
return true;
}
main.cpp
#include <iostream>
#include "data_structure.h"
using namespace A;
int main( int argc, char **argv ) {
A::B s;
s.func_init();
return 0;
}
I have an error as the following
undefined reference to `A::B::func_init()'
Please kindly advice why I can not get the func_init, eventhough it is declared as public? I have put also the correct namespace there.
Would appreciate for any response.
That's a linker error, so you're probably not compiling all your source files, or linking them together, or making some weird use of the C compiler (I see your files have the extension .c, some compilers treat them as C-source).
g++ main.cpp data_structure.cpp -o test should do it.
However I did need to add #include <iostream> to your data_structure.cpp file to resolve
data_structure.cpp: In member function ‘bool A::B::func_init()’:
data_structure.cpp:7:5: error: ‘cout’ is not a member of ‘std’
data_structure.cpp:7:33: error: ‘endl’ is not a member of ‘std’
and make it compile.
The definition of a function has to be in the namespace that declares the function. A using declaration just pulls in names from the namespace; it doesn't put you inside it. So you have to write data_structure.cpp like this:
#include "data_structure.h"
#include <iostream>
namespace A {
bool B::func_init() {
std::cout << "test init" << std::endl;
return true;
}
}
Or, if you prefer, you can use the namespace name explicitly in the function definition:
bool A::B::func_init() {
std::cout << "test init" << std::endl;
return true;
}
Have you tried not putting
using namespace A;
in your data_structure.cpp file and instead putting:
#include "data_structure.h"
bool A::B::func_init() {
std::cout << "test init" << std::endl;
return true;
}
I have the feeling that when you use using namespace A; doesn't let you append function definitions to the namespace, but only tells the compiler/linker where to look for Types or Functions...
Another theory:
Have you tried nesting your CPP code in the same namespace?
#include "data_structure.h"
namespace A {
bool B::func_init() {
std::cout << "test init" << std::endl;
return true;
}
}
I have no idea why this doesn't work
#include <iostream>
#include <pthread.h>
using namespace std;
void *print_message(){
cout << "Threading\n";
}
int main() {
pthread_t t1;
pthread_create(&t1, NULL, &print_message, NULL);
cout << "Hello";
return 0;
}
The error:
[Description, Resource, Path, Location, Type] initializing argument 3
of 'int pthread_create(pthread_t*, const pthread_attr_t*, void*
(*)(void*), void*)' threading.cpp threading/src line 24 C/C++
Problem
You should declare the thread main as:
void* print_message(void*) // takes one parameter, unnamed if you aren't using it
Because the main thread exits.
Put a sleep in the main thread.
cout << "Hello";
sleep(1);
return 0;
The POSIX standard does not specify what happens when the main thread exits.
But in most implementations this will cause all spawned threads to die.
So in the main thread you should wait for the thread to die before you exit. In this case the simplest solution is just to sleep and give the other thread a chance to execute. In real code you would use pthread_join();
#include <iostream>
#include <pthread.h>
using namespace std;
#if defined(__cplusplus)
extern "C"
#endif
void *print_message(void*)
{
cout << "Threading\n";
}
int main()
{
pthread_t t1;
pthread_create(&t1, NULL, &print_message, NULL);
cout << "Hello";
void* result;
pthread_join(t1,&result);
return 0;
}
When compiling with G++, remember to put the -lpthread flag :)
From the pthread function prototype:
int pthread_create(pthread_t *thread, const pthread_attr_t *attr,
void *(*start_routine)(void*), void *arg);
The function passed to pthread_create must have a prototype of
void* name(void *arg)
This worked for me:
#include <iostream>
#include <pthread.h>
using namespace std;
void* print_message(void*) {
cout << "Threading\n";
}
int main() {
pthread_t t1;
pthread_create(&t1, NULL, &print_message, NULL);
cout << "Hello";
// Optional.
void* result;
pthread_join(t1,&result);
// :~
return 0;
}
Linkage. Try this:
extern "C" void *print_message() {...