Параллелизм C-программы с pthread - PullRequest
1 голос
/ 14 декабря 2011


Я делаю обзор с запиской лекции моего профессора.Я получил этот вопрос, когда добрался до секции параллелизма:
на слайде профессор привел два примера использования pthread (один хороший пример, а другой плохой).Но я не понимаю, почему между ними есть разница.
Вот хороший пример:

#include <stdio.h> 
#include <stdlib.h> 
#include <pthread.h> 
void *get_rand_num(void *args) { 
  int *nump = malloc(sizeof(int)); 
  srand(pthread_self()); 
  *nump = rand(); 
  return nump; 
} 
int main() { 
  pthread_t tid; 
  void *ptr = NULL; 
  pthread_create(&tid, NULL, get_rand_num, NULL); 
  pthread_join(tid, &ptr); 
  printf("Random number: %d\n", * (int *) ptr); 
  return 0; 
}

И плохой пример

#include <stdio.h> 
#include <stdlib.h> 
#include <pthread.h> 
void *get_rand_num(void *args) { 
  int num; 
  srand(pthread_self()); 
  num = rand(); 
  return &num; 
} 
int main() { 
  pthread_t tid; 
  void *ptr = NULL; 
  pthread_create(&tid, NULL, get_rand_num, NULL); 
  pthread_join(tid, &ptr); 
  printf("Random number: %d\n", * (int *) ptr); 
  return 0; 
}

Любой может понять эти два примера, пожалуйста, объясните мне, почему плохой отличается отПервый, а почему это не хорошо?


Спасибо
Аллан

Ответы [ 3 ]

5 голосов
/ 14 декабря 2011

Плохой пример возвращает указатель на локальную переменную. Это всегда плохая идея, потому что локальные переменные умирают, когда функция возвращается. Это не проблема, специфичная для многопоточных программ, но усугубляется тем, что потоки получают один стек на поток, который освобождается после pthread_join. В то время как вам часто везет в однопоточном программировании и вы можете использовать указатель сразу после возврата функции, весь сегмент, содержащий стек старого потока, мог вернуться в операционную систему в плохом примере, и доступ приведет к ошибкам сегментации. *

Первый пример также не очень хорош, поскольку вызывает утечку памяти.

1 голос
/ 14 декабря 2011

В плохом случае ваш return & num, где num - это локальная переменная в стеке, которая действительна только в области действия функции. Как только вы вернетесь, он больше не действителен.

0 голосов
/ 14 декабря 2011

Плохой регистр возвращает указатель на бит стека - как птица, которая давно вылетела из окна!

Но если это сработает - у вас будет очень и очень случайное число - немного лучше, чем сортировка случайного числа с идентификатором потока!

...