[英]C language and multithread programming
我的問題與 C 中的線程編程有關。
我的問題是我只想在我的main
中創建兩個線程。 這兩個線程應該按順序工作,這意味着我的第一個線程應該首先執行(不應執行任何線程的其他語句)。 第一個線程應該有完全的控制權。 在第一個線程完成之前,不應執行任何其他線程的其他語句,甚至是main
語句。
第一個線程完成后,第二個線程應該以與第一個線程類似的方式執行。
之后我的主要應該執行。
我知道你可以說我為什么要這樣做,因為這可以通過創建兩個函數並按順序調用它們來實現,但是為了學習和實驗,我想在線程的幫助下完成。
我在 C 中寫了一些代碼如下:
void* fun()
{
printf("\nThe thread 1 is running");
}
void* van()
{
printf("\nthread 2 is running ");
}
int main()
{
pthread_t t1,t2;
pthread_create(&t1,NULL,fun,NULL);
pthread_create(&t2,NULL,van,NULL);
printf("\nI'm in main\n");
pthread_join(t2,NULL);
}
該程序運行良好,但我不理解 function pthread_join()
的工作。
當我按如下方式更改我的代碼時:
int main()
{
pthread_t t1,t2;
pthread_create(&t1,NULL,fun,NULL);
pthread_join(t2,NULL); // Change
pthread_create(&t2,NULL,van,NULL);
printf("\nI'm in main\n");
}
現在,當我運行代碼時,它會顯示分段錯誤。
現在我的問題如下:
pthread_create()
function 中的屬性參數是什么? 我們為什么要使用它們? 線程的默認屬性是什么? 請舉例說明。pthread_create()
function 中的參數是什么? 我們為什么要使用它們? 線程的默認 arguments 是什么? 請舉例說明。pthread_join()
實際上是如何工作的? 當我的代碼以t2
作為第一個參數在 main 中調用pthread_join()
時,這是什么意思。 這是否意味着 main 應該暫停執行,直到 t2 執行完成或其他什么?pthread_join()
中的第二個參數是什么? 我們為什么用它? 它的默認值是多少? 請用示例或代碼解釋。attr 參數指向一個 pthread_attr_t 結構,其內容在線程創建時用於確定新線程的屬性; 這個結構是使用pthread_attr_init(3)和相關函數初始化的。 如果 attr 是 NULL,則使用默認屬性 ( source ) 創建線程。
參數被傳遞給你的線程 function。 這是將數據傳遞給線程的最佳方式(與使用全局變量相反,例如)。
是的, pthread_join
一直等到線程完成。 這就是為什么在啟動線程之前調用pthread_join
時程序會失敗的原因,因為此時 t2 包含垃圾。
如果 retval 不是 NULL,則 pthread_join() 將目標線程的退出狀態(即目標線程提供給 pthread_exit(3) 的值)復制到 *retval 指向的位置。 如果目標線程被取消,則 PTHREAD_CANCELED 被放置在 *retval 中。 ( 來源)。
即,您可以使您的線程 function 通知您其執行結果。
鑒於此,您的線程創建可能如下所示:
struct th_arg{
...
};
static void th_work(struct th_arg* a){
//...some work
if (success) pthread_exit(EXIT_SUCCESS)
else pthread_exit(ERROR_CODE);
}
int main(){
int t1,t2;
struct th_arg[2];
int codes[2];
// initialize th_arg2
pthread_create(&t1, NULL, th_work, th_arg+0, th_arg+0);
pthread_create(&t2, NULL, th_work, th_arg+1, th_arg+1);
pthread_join(t1, codes+0);
pthread_join(t2, codes+1);
if (codes[0] == EXIT_SUCCESS && codes[1] == EXIT_SUCCESS){
...
}
}
學習 posix 線程的最佳來源是https://computing.llnl.gov/tutorials/pthreads/
pthread_attr_t
中的屬性屬於pthread_create
類型。 它保存有關線程的信息,包括線程的 memory 地址從哪里開始以及它的堆棧可以達到多大。 大多數情況下,您不需要使用此參數。
pthread_create
中的 arg 作為唯一的參數傳遞給start_routine
function。 這是一種黑客行為。 由於指針可以指向任何東西(int、數組、結構等),因此您可以通過將指針傳遞給您要傳入的所有數據來傳入 arguments。大多數時候人們最終會選擇一個結構。 線程沒有默認的 arguments。 如果您不想傳入任何內容,只需將arg
指定為 NULL。
舉個例子:
struct arguments
{
int something;
char* anotherArg;
short stillAnotherArg;
}
void* fun(void* arg)
{
struct arguments *my_args = (struct arguments*)arg;
printf("You said: %s\n", my_args->anotherArg); // Will print "You said: Hello there"
...
}
int main()
{
pthread_t t1;
struct arguments my_args;
my_args.something = 5;
my_args.anotherArg = "Hello there";
my_args.stillAnotherArg = 42;
pthread_create (&t1,NULL,fun, &my_args);
...
}
pthread_join
阻塞調用者,直到指定的線程完成。
pthread_join
的第二個參數允許您捕獲線程執行完成后的返回值。 您的每個線程都返回一個void*
,第二個參數允許您指定該返回值的存儲位置。
舉個例子:
void* fun(void* arg)
{
...
return NULL; // not very exciting, but I don't want to get
// into memory management problems right now
}
int main()
{
...
void* theReturnValue;
pthread_join(t2, &theReturnValue);
printf("fun returned %p\n", theReturnValue); // will print "fun returned 0x0"
// which is NULL
}
最后,它出現段錯誤的原因是因為您正在等待尚未定義的線程。
您可以通過包含omp.h來使用omp庫。 它很容易使用。 您可以使用指令創建並行部分
#pragma omp parallel
{
// PARALLEL Code
}
並使用omp_set_num_threads(2);
然后使用omp_get_thread_num();
例子:
omp_set_num_threads(2);
#pragma omp parallel
{
printf("thread %d said hello", omp_get_thread_num());
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.