C++文件处理工具类,hpp文件,使用时只需要include即可,跨平台

C++文件处理工具类,hpp文件,使用时只需要include即可,跨平台

File.hpp

#ifndef FILE_HPP
#define FILE_HPP

#include <fstream>
#include <string>
#include <stdexcept>
#include <memory>
#include <sstream>
#include <unistd.h>

#include<sys/stat.h>

namespace sh
{
enum class FileMode
{
EXISTS = 0,//存在
EXECUTE = 1,//执行
WRITE = 2,//写
READ = 4//读
};

/**
* 文件操作
* @author: sherlock_lht
*/
class BaseFileIO
{

protected:

std::fstream fileStream;
std::string fileName;

explicit BaseFileIO(const std::string &fileName)
{
this->fileName = fileName;
}
public:
/**
* 检查文件是否存在
*/
static bool exists(const std::string &filePath)
{
return access(filePath.c_str(), F_OK) == 0;
}

/**
* 检查指定文件的指定属性,包括是否存在、是否可读、是否可写、是否有权限执行
*/
static bool checkFileMode(const std::string& filePath, sh::FileMode mode)
{
return access(filePath.c_str(), (int)mode) == 0;
}

/**
* 给指定文件赋予权限,同chmod指令
*/
static bool chmodFile(const std::string &filePath, int mode)
{
return chmod(filePath.c_str(), mode) == 0;
}

public:
/**
* 打开文件,返回是否成功打开
*/
bool open(std::ios_base::openmode mode)
{
if (fileStream.is_open())
{
close();
}
fileStream.open(fileName, mode);
return fileStream.is_open();
}

/**
* 设置文件的开始读取偏移
*/
void seekInputPosition(std::size_t offsetPosition, std::ios_base::seekdir position = std::ios::beg)
{
fileStream.seekg(offsetPosition, position);
}

/**
* 是否已经读到end,可用此方法判断文件是否已经读完
*/
bool endOfFile() const
{
return fileStream.eof();
}

/**
* 获取当前处理的文件名称
*/
std::string getFileName() const
{
return fileName;
}

/**
* 关闭文件流,如果从未打开,则无任何操作
*/
void close()
{
if (fileStream.is_open())
{
fileStream.close();
}
}

virtual ~BaseFileIO()
{
close();
}
};

class File: public BaseFileIO
{
public:
/**
* 向指定的文件写入指定的内容,返回值表示是否写入成功
*/
static bool saveTextTo(const std::string &fileName, const std::string &text)
{
File fileToWrite(fileName);
if (fileToWrite.open(std::ios::out | std::ios::app))
{
fileToWrite.write(text);
fileToWrite.close();
return true;
}
return false;
}
public:

explicit File(const std::string &fileName)
: BaseFileIO(fileName)
{}

/**
* 写入内容,返回值表示写入成功的长度
*/
std::size_t write(const std::string &content)
{
auto before = fileStream.tellp();
fileStream.write(content.data(), content.length());
return fileStream.tellp() - before;
}

/**
* 读取所有文件内容
* offset参数表示开始读取的偏移
* 如果在调用之前有读取过文件,则会影响该函数的开始读取位置
*/
std::string readAll(std::size_t offset = 0)
{
if (!fileStream.is_open())
{
return "";
}
if (offset > 0)
{
seekInputPosition(offset);
}
std::stringstream buf;
buf << fileStream.rdbuf();
return buf.str();
}

/**
* 读取指定数量的字符串,如果内容不够,则读完
* offset参数表示开始读取的偏移
* 读取位置置于本次最后读取的内容的结尾
*/
std::string read(std::size_t maxSize, std::size_t offset = 0)
{
if (!fileStream.is_open())
{
return "";
}
if (offset > 0)
{
seekInputPosition(offset);
}
std::unique_ptr<char[]> buf(new(std::nothrow) char[maxSize + 1]);
fileStream.read(buf.get(), maxSize);
std::size_t size = fileStream.gcount();
std::string str(buf.get(), size);
return str;
}

/**
* 从标记开始位置读取到一行结尾,包括终止符
* offset参数表示开始读取的偏移
*/
std::string readLine(std::size_t maxSize, std::size_t offset = 0)
{
if (!fileStream.is_open())
{
return "";
}

std::unique_ptr<char[]> buf(new(std::nothrow) char[maxSize + 1]);
fileStream.getline(buf.get(), maxSize);
std::size_t size = fileStream.gcount();
std::string str(buf.get(), size);
return str;
}
};
}

#endif //FILE_HPP