linux下实现程序异步执行

目标:main()函数调用数据采集函数,在main函数结束并返回后,数据采集函数仍然可以执行

尝试1:多线程 muliple threads

思想:使用pthread_create()函数在main函数内创建新线程,期望main函数的结束不会影响子线程,使其能长期执行下去

实验代码:

#include <pthread.h>
#include <iostream>
#include <sys/wait.h>

using namespace std;

pthread_t id_thread_1,id_thread_2;

int data_common;
pthread_mutex_t lock_threads = PTHREAD_MUTEX_INITIALIZER;

void * add(void *arg)
{
  for(int k = 0;k<20;k++)
    {
      usleep(200000);
      pthread_mutex_lock(&lock_threads);
      data_common+= 321;
      cout<<"function add is executing..." <<data_common<<endl;
      pthread_mutex_unlock(&lock_threads);
    }
  return ((void *)0);
}

void * sub(void *arg)
{
  for(int m=0;m<30;m++)
    {
      usleep(300000);
      pthread_mutex_lock(&lock_threads);
      data_common -= 91;
      cout<<"function sub is executing..." <<data_common<<endl;
      pthread_mutex_unlock(&lock_threads);
    }
  return ((void *)0);
}

int main(int argc,char **argv)
{
  int err;
  void *tret;
  err = pthread_create(&id_thread_1,NULL,add,NULL);
  if(err!=0)
    {
      cerr << "pthread_create(add) error !"<<endl;
      exit(-1);
    }
  err = pthread_create(&id_thread_2,NULL,sub,NULL);
  if(err!=0)
    {
      cerr << "pthread_create(add) error !"<<endl;
      exit(-1);
    }
  err = pthread_join(id_thread_1,&tret);
  if(err !=0)
    {
      cerr << "can not join with thread "<< id_thread_1 <<endl;
      exit(-1);
    }
  err = pthread_join(id_thread_2,&tret);
  if(err !=0)
    {
      cerr << "can not join with thread "<< id_thread_2 <<endl;
      exit(-1);
    }

  return 0;
}
结果:

1。如果主线程不等待子线程结束就直接返回,那么子线程当即死亡(仅仅指在终端看不到执行结果)

2。如果主线程等待子线程执行结束再返回,那么所有线程将同步结束

结论:使用线程的方法行不通,尝试1失败。

尝试2:使用软定时器+信号

思想:使用软定时器,每隔一定时间,就产生一个指定的信号。而将需要定期执行的函数设置为该信号的处理函数。以此来实现函数的定期执行。

实验代码:

#include  <signal.h> 
#include  <sys/time.h> 

#include <sys/wait.h>
#include  <string.h> 
#include  <stdio.h> 

#include <unistd.h>

const char *prompt="时间已经过去了0.5秒钟\n";  
unsigned int len;   
void prompt_info(int signo)  
{
	printf(prompt);
	//write(STDERR_FILENO,prompt,len);  
}
void init_sigaction(void)
{
	struct sigaction act;
	act.sa_handler=prompt_info;//信号处理函数
	act.sa_flags=0;
	sigemptyset(&act.sa_mask);//用来将act.sa_mask信号集初始化并清空
	sigaction(SIGALRM,&act,NULL);//查询活设置信号处理方式
}

void init_time()
{
	struct itimerval value;
	value.it_value.tv_sec=0;
	value.it_value.tv_usec=500000;
	value.it_interval=value.it_value;
	setitimer(ITIMER_REAL,&value,NULL);
}

int main()
{
	len=strlen(prompt);
	init_sigaction();
	init_time();
	usleep(4000000);
 return 0;
}

实验结果:函数执行完毕时软定时器自动失效。函数进入sleep状态后软定时器也失效。

结论:软定时器方法无效,失败。

尝试3:使用fork函数 创建新进程

思想:函数被调用时由父进程返回,子进程继续处理数据。

实验代码:

#include <iostream>
#include <sys/wait.h>
#include <sys/types.h>
#include <unistd.h>
#include <cstring>
using namespace std;
pid_t sub()
{
  pid_t pd;
  char *cmd;
  pd = fork();
  switch(pd)
    {
    case -1:
      cout << "fork() error !"<<endl;
      return 1;
    case 0:
      cout << "This is the child process ."<<endl;
      goto label_child;
    default:
      cout << "My child process pid ="<<pd<<endl;
      goto label_parent;
    }
label_child:
  cmd= new char[2];
  memset(cmd,0,2*sizeof(char));
  *cmd=0x0d;
  cout <<"Child process executing ..."<<endl;
  usleep(1000);
  for(int m =10;m<123456;m++)
    {
      printf("%8d",m);
      fflush(stdout);
      usleep(10000);
      printf(cmd);
    }
  free(cmd);
  return 0;
label_parent:
  return pd;

}
int main()
{
  pid_t p = sub();
  cout << "Child is still executing ..."
          "Press any key to kill the child."<<endl;
  getc(stdin);
  char *cmd = new char[100];
  memset(cmd,0,100*sizeof(char));
  sprintf(cmd,"kill %d",p);
  system(cmd);
  free(cmd);
  cout << "Game over!"<<endl;
  return 0;
}


实验结果:可以实现函数调用结束后继续执行的功能。

结论:成功


尝试4:使用定时器+中断处理函数

实验代码:未做 ^_^

结果:应该比前几个都要好


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

sanzhong104204

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值