我有一组 n 个线程,需要编号为0到 n - 1。
这个不太好用。
#include <pthread.h>
#include <stdio.h>
#define MY_THREAD_COUNT 6
void *runner(void *param) {
int id = *(int*)param;
printf("Thread %d\n", id);
}
int main() {
pthread_t thread_arr[MY_THREAD_COUNT];
for (int i = 0; i < MY_THREAD_COUNT; i++)
pthread_create(&thread_arr[i], NULL, runner, &i);
for (int i = 0; i < MY_THREAD_COUNT; i++)
pthread_join(thread_arr[i], NULL);
}
它会产生如下输出:
线程2
线程2
线程3
线程4
线程5
线程6
为每个线程的ID号创建一个指针 * 确实 * 正确:
for (int i = 0; i < MY_THREAD_COUNT; i++) {
int *tmp = malloc(sizeof(int));
*tmp = i;
pthread_create(&thread_arr[i], NULL, runner, tmp);
}
它会产生如下输出:
线程0
线程1
线程2
线程4
线程5
线程3
然而,由于它需要错位,泄漏,yada yada,这不是我理想的解决方案。
有没有办法从runner()
内部调用的函数中获取id号?类似于pthread_self()
,但它会给予序列号,从0到 n - 1?
或者--更广泛地打开问题--什么是总体上最干净的方式来做到这一点?如果有任何方法摆在桌面上,你认为什么是最好的?
2条答案
按热度按时间9w11ddsr1#
您看到的结果是因为您无法保证创建的线程何时会相对于
main
线程运行。将i
的地址传递给runner
。每次都是相同的地址,所以i
中的任何值都是runner
运行时看到的。更糟糕的是,for
循环可能在线程运行之前终止(这解释了你的6)。.你只是运气好,当发生这种情况时,6,runner
正在访问范围外的内存。一个可能的解决方案:
这将在运行时期间将参数保持在作用域中。
lf5gs5x22#
您可以执行以下操作:
这样就不会有传递给子线程的参数的生存期问题。