多线程读写文件问题

多线程读写同个文件会不会有访问冲突或者异常?我们写个程序来测试一下

/**
 * Created by fangruibin
 * 测试多线程读写文件
 */

#include <iostream>
#include <pthread.h>
#include <unistd.h>
#include <string.h>

const char* fileName = "test.txt";

void processRead()
{
  FILE* fp = fopen(fileName, "r");
  if (fp == NULL)
  {
    printf("open file for read failed\n");
    return;
  }
  
  // 获取文件长度
  long startPos = ftell(fp);
  fseek(fp, 0, SEEK_END);
  long endPos = ftell(fp);
  long fileSize = endPos - startPos;
  fseek(fp, 0, SEEK_SET);
  
  char* pBuf = (char*)malloc(fileSize + 1);
  size_t readSize = fread(pBuf, 1, fileSize, fp);
  if ((long)readSize != fileSize)
  {
    printf("read not complete %ld\n", (long)readSize);
  }
  pBuf[fileSize] = '\0';
  if (strlen(pBuf) == 0)
  {
    printf("read empty\n");
  }
  printf("read:\n%s\n", pBuf);
  
  free(pBuf);
  fclose(fp);
}

void processWrite()
{
  FILE* fp = fopen(fileName, "w");
  if (fp == NULL)
  {
    printf("open file for write failed\n");
    return;
  }
  
  const char* pData = "2222222222222222222222222222\n2222222222222222222222222222\n2222222222222222222222222222\n";
  size_t dataLen = strlen(pData);
  size_t writeLen = fwrite(pData, 1, dataLen, fp);
  if (dataLen != writeLen)
  {
    printf("write not complete %ld\n", (long)writeLen);
  }
  fclose(fp);
}

void processReadWrite(const char* pData)
{
  FILE* fp = fopen(fileName, "w+");
  if (fp == NULL)
  {
    printf("open file for read&write failed\n");
    return;
  }
  
  size_t dataLen = strlen(pData);
  size_t writeLen = fwrite(pData, 1, dataLen, fp);
  if (dataLen != writeLen)
  {
    printf("write not complete %ld\n", (long)writeLen);
  }
  
  // 获取文件长度
  fseek(fp, 0, SEEK_SET);
  long startPos = ftell(fp);
  fseek(fp, 0, SEEK_END);
  long endPos = ftell(fp);
  long fileSize = endPos - startPos;
  fseek(fp, 0, SEEK_SET);
  
  char* pBuf = (char*)malloc(fileSize + 1);
  size_t readSize = fread(pBuf, 1, fileSize, fp);
  if ((long)readSize != fileSize)
  {
    printf("read not complete %ld\n", (long)readSize);
  }
  pBuf[fileSize] = '\0';
  printf("[rw] read:\n%s\n", pBuf);
  
  free(pBuf);
  fclose(fp);
}

//线程1
void* threadFunc1(void* p)
{
  while (1)
  {
    // const char* pData = "111111111111111111111111111\n111111111111111111111111111\n";
    // processReadWrite(pData);
    processRead();
    usleep(100 * 1000);
  }
  
  return NULL;
}

//线程2
void* threadFunc2(void* p)
{
  while (1)
  {
    // const char* pData = "222222222222222222222222222\n222222222222222222222222222\n";
    // processReadWrite(pData);
    processWrite();
    usleep(100 * 1000);
  }
  
  return NULL;
}

int main()
{
  //初始化线程
  pthread_t hThread1;
  pthread_t hThread2;
  if (pthread_create(&hThread1, NULL, &threadFunc1, NULL) != 0)
  {
    printf("create thread 1 failed\n");
    return -1;
  }
  if (pthread_create(&hThread2, NULL, &threadFunc2, NULL) != 0)
  {
    printf("create thread 2 failed\n");
    return -1;
  }
  
  while (1)
  {
    sleep(1);
  }
  
  return 0;
}

代码中我们设计了两个线程,第一个线程从test.txt文件中读内容,第二个线程不断地向test.txt文件写入内容,然后我们看看读出来的内容和我们写入的内容是不是一样的

运行结果:

fang@fang-deepin:~/dev/chrifang/test/cpp/file$ ./multi_thread 
read:
2222222222222222222222222222
2222222222222222222222222222
2222222222222222222222222222

read not complete 0
read empty
read:

read not complete 0
read empty
read:

read not complete 0
read empty
read:

read empty
read:

read not complete 0
read empty
read:

read not complete 0
read empty
read:

read empty
read:

read:
2222222222222222222222222222
2222222222222222222222222222
2222222222222222222222222222

可以看到有很多读取结果为空的,证明多线程读写文件是会有访问冲突的。如何避免冲突呢?

1) 同个进程内读写文件加上线程锁

2) 不同进程读写文件使用flock()函数去加锁

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值