哎,我的博客真的没人看啊,到目前为止才有5个人看,其中一个还是版主,估计其他四个看了之后也是万分后悔啊,我忍,做技术的人就是要忍受寂寞
每次都觉得自己好肤浅,今天又碰到肤浅的问题了
就是线程创建时的问题
pthread_create
int pthread_create(pthread_t * thread, pthread_attr_t * attr,void * (*start_routine)(void *), void * arg);
可见,参数3是指向线程函数的函数指针。说白了参数是一个void *类型。
首先,我写了一个错误的代码,如下:
#include <stdlib.h>
#include <stdio.h>
#include <pthread.h>
pthread_t thread_id= NULL;
int gps_proc()
{
  int i;
   for(i=0;i<10;i++)
  {
            printf( "11111111111111111111111111111111111111111\n");
            sleep(1);
  }
   exit(0);//此处有错,因为exit退出了进程,应该是return 0;8.26 修正
}
int main( void )
{
    int ret;
    int i;
    ret=pthread_create(&thread_id, NULL,(int*)gps_proc(), NULL);
     if(ret!=0){printf( "Create pthread error!\n");return -1;}
     for(i=0;i<10;i++)
    {
            printf( "22222222222222222222222222222222222222222\n");
            sleep(1);
     }
     return 0;
}
编译没有任何错误,执行,
打印10行 111111111111111111111111111111
然后segmentfault
在高手的指点之下,我改正了,代码又如下:
#include <stdlib.h>
#include <stdio.h>
#include <pthread.h>
pthread_t thread_id= NULL;
int gps_proc()
{
    int i;
     for(i=0;i<10;i++)
    {
            printf( "11111111111111111111111111111111111111111\n");
            sleep(1);
    }
     exit(0);
}
int main( void )
{
     int ret;
     int i;
     ret=pthread_create(&thread_id, NULL,(int*)gps_proc, NULL);
      if(ret!=0){printf( "Create pthread error!\n");return -1;}
      for(i=0;i<10;i++)
     {
            printf( "22222222222222222222222222222222222222222\n");
            sleep(1);
     }
     return 0;
}
也就是说,在gps_proc后面的()去掉就行了
可是,为什么呢?
想想看,第三个参数是个void*,也就是说,它要的是一个地址,地址是什么,无非就是一个数值,
我们用gps_info()的时候,这是一个函数,调用的时候得到的是返回值,是个数值,编译的时候把它当地址对待,前面加 int* 的强制类型转化无非就是想说这个地址里面的内容读出时按int类型解读,组合。所以,我写成gps_info()是可以编译通过的,但是为什么只输出10行1111111111111111111111111,然后segmentfault的错误呢?因为要想得到这个函数的返回值,首先要把这个函数执行一遍先,所以,我们的函数就去执行了,执行了之后呢?返回0,我们认为这是地址0,可是地址0是什么呢?有没有被什么其他人预先用了呢?自然而然,就发生了segmentfault的错误。
而用 gps_info 这个表示的就是函数的地址,我们也可以理解为函数的入口地址啊,至于为什么正确,我就不做过错解释了,因为我们已经从错误中汲取了足够的教训。