在单台机器上实现TB级的数据对比之数据切分

RAG文本切分实战指南:语义锚定与工程化切分策略 文本切分是RAG系统中决定检索质量的基础环节,其本质并非简单字符切割,而是面向语义建模的预处理动作。通过构建语义锚点、控制chunk粒度、保留上下文连贯性,可显著提升向量检索的准确性与鲁棒性。关键技术价值在于缓解语义碎片化与噪声稀释问题,支撑法律合同解析、技术文档问答、代码知识检索等高精度场景。本文聚焦真实生产环境中的切分策略选型、RecursiveCharacterTextSplitter深度调优、Markdown与代码文档增强切分,以及语义密度(SD)评估方法,直击RAG落地中最常被低估的命门——文本切 阅读详情

在单台机器上实现TB级的数据对比之数据切分

文件切分的逻辑

由于面对的原始文件可能是一堆小文件,也可能是一个很大文件,这第一步当然是对文件进行切割规整,统一大小为32M,这个32M是一个近似值,由于要保留完整的行,故这是一个接近值。那如何实现呢?

分为两部分来说吧,

第一部分是文件读取:

  1. 读取目录下的文件,获得一个文件列表。列表使用数组来存储。
  2. 将列表按文件名进行排序,获得数据读取文件的一个顺序,也就是数据的一个顺序。
  3. 声明一个索引编号,编号从0开始,这个索引编号代表的就是当前正在读取的文件。
  4. 按索引编号在文件列表中读取。打开字符流。
  5. 按行读取文件。直到一个文件结束。
  6. 当一个文件读取结束时,关闭当前文件流。将文件索引编号加1,再次打开下一个文件的字符流。
  7. 继续按行读取。直到所有文件都结束。
  8. 当文件操作完毕后,数据流将自动关闭。

第二部分是文件写入:与文件读取是类似的打开

  1. 当然是指定文件的写入路径了,以及文件名增长规则。我使的规则较简单为:xxx-0.txt.ing和xxx-0.txt,在写入中以.ing结束,写入完成的被重命名为xxx.txt。
  2. 声明一个写入索引。编号从0开始。这个索引代表的就是当前正常写入的文件,这个索引编号是文件名的一部分。
  3. 打开写入字符流。
  4. 按行进行数据的写入。直到文件到达临界值32M。
  5. 当达到32M时,关闭当前文件流,文件重命名,将.ing去除。再将写入索引加1,再次打下写入文件字符流。
  6. 继续按行写入,直接所有文件都写入完成。
  7. 当文件操作完毕后,数据流将自动关闭。

最后我解释下为什么是32M。其实这个我是参照了HDFS的文件块的大小设计。在内存占用与磁盘传输方面取了一个折中值。
当然如果内存允许,可以将这个值调的更大,64M,128M都是可以的。
这个受到两方面的一个限制
限制1:单文件如果过大,那么加载到内存中排序的内存需求量也要更大。在普通机器这个限制较多。毕竟不是服务器,内存都128G起步的。
限制2:单文件如果过小,那以文件的IO效率必然降低,我们都知道,磁盘这种设备顺序读写速度较高,随机访问却很低。基于这个特性单文件就不能太小。否则IO会成为瓶颈。

示例图

联合起来就是就是下面这样子:

在这里插入图片描述

这就是文件切分的一个过程。

读取的代码实现

最后来看看代码吧!

/**
 * 多文件读取操作
 *
 * @author liujun
 * @version 0.0.1
 */
public class ManyFileReader implements AutoCloseable {

  /** 每次读取0124条记录 */
  private static final int BATCH_READ_LIST = 1024;

  /** 基础的文件路径 */
  private String path;

  /** 文件操作路径 */
  private final File[] fileData;

  /** 当前读取的索引编号 */
  private int readIndex;

  /** 字符流的读取 */
  private FileReader fileReader;

  /** 带缓冲区的字符流 */
  private BufferedReader bufferedReader;

  public ManyFileReader(String path) {
    this.path = path;
    File[] fileDataTmp = FileUtils.getFileList(this.path);
    // 执行默认的文件排序操作
    Arrays.sort(
        fileDataTmp,
        (o1, o2) -> {
          int index1 = getFileIndex(o1);
          int index2 = getFileIndex(o2);
          if (index1 < index2) {
            return -1;
          } else if (index1 > index2) {
            return 1;
          }
          return 0;
        });
    this.fileData = fileDataTmp;
    this.readIndex = 0;
  }

  /**
   * 读取,带排序的操作
   *
   * @param path
   * @param comparator
   */
  public ManyFileReader(String path, Comparator<File> comparator) {
    this.path = path;
    this.readIndex = 0;
    File[] files = FileUtils.getFileList(this.path);
    // 执行文件的排序操作
    Arrays.sort(files, comparator);
    this.fileData = files;
  }

  /** 文件通道打开,首次操作,需要明确调用打开文件通道 */
  public void openFile() {
    if (this.readIndex >= this.fileData.length) {
      return;
    }

    try {
      this.fileReader = new FileReader(this.fileData[readIndex]);
      this.bufferedReader = new BufferedReader(this.fileReader);
    } catch (FileNotFoundException e) {
      e.printStackTrace();
    }
  }

  /**
   * 每次读取一行数据
   *
   * @return
   */
  public String readLine() throws IOException {
    String dataLine = null;

    dataLine = this.bufferedReader.readLine();

    // 文件读取行结束,切换到下一行
    if (dataLine == null) {
      boolean nextFile = this.nextFile();
      // 当文件切换成功后,需要再读取一次数据,保证连续读取
      if (nextFile) {
        dataLine = this.bufferedReader.readLine();
      }
    }

    return dataLine;
  }

  /**
   * 批量读取数据
   *
   * @return 批量数据集
   * @throws IOException 异常信息
   */
  public List<String> readLineList() throws IOException {
    List<String> dataList = new ArrayList<>(BATCH_READ_LIST);

    for (int i = 0; i < BATCH_READ_LIST; i++) {
      String dataLine = this.readLine();
      if (null != dataLine) {
        dataList.add(dataLine);
      } else {
        break;
      }
    }
    return dataList;
  }

  /** 文件再次重新读取 */
  public void reload() {
    this.readIndex = 0;
  }

  /** 文件关闭操作 */
  @Override
  public void close() {
    if (null != this.bufferedReader) {
      IOUtils.close(this.bufferedReader);
    }
    if (null != this.fileReader) {
      IOUtils.close(this.fileReader);
    }
  }

  /**
   * 切换到下一个文件
   *
   * @return
   */
  private boolean nextFile() {
    // 切换到一个文件索引
    this.readIndex++;
    // 当文件读取索引大于文件个数时,执行退出
    if (this.readIndex >= this.fileData.length) {
      return false;
    }
    // 1,当一个文件读取完成后,执行对文件的关闭操作
    this.close();
    // 切换成功后,打开下一个文件通道
    this.openFile();

    return true;
  }

  /**
   * 默认按文件索引号进行排序
   *
   * @param file
   * @return
   */
  private int getFileIndex(File file) {
    String name = file.getName();
    int suffixIndex = name.lastIndexOf(Symbol.POINT);
    int spitIndex = name.lastIndexOf(Symbol.MINUS);
    return Integer.parseInt(name.substring(spitIndex + Symbol.MINUS.length(), suffixIndex));
  }
}

写入的代码实现

文件写入,由于文件写入我支持两种模式,一种为按行切分,还有一种为按大小切分。故将写入的基础类义为一个抽象类

/**
 * 多文件写入操作,基础类
 *
 * @author liujun
 * @version 0.0.1
 */
public abstract class AbstractManyFileWrite implements AutoCloseable {

  /** 正在文件写入标识 */
  private static final String WRITE_ING_FLAG = CompareConfig.TEXT_SUFFIX_NAME_ING;

  /** 写入的文件后缀名 */
  private static final String WRITE_FILE_SUFFIX_NAME = CompareConfig.TEXT_SUFFIX_NAME;

  /** 基础的文件路径 */
  private final String path;

  /** 输出的文件名 */
  private final String fileName;

  /** 当前写入的编写 */
  private AtomicInteger writeIndex;

  /** 文件写入 */
  private FileWriter writer;

  /** 带缓冲区的文件写入 */
  private BufferedWriter bufferedWriter;

  /**
   * 多路文件写入
   *
   * @param path 文件路径
   * @param fileName 文件名称
   */
  public AbstractManyFileWrite(String path, String fileName) {
    this.path = path;
    this.fileName = fileName;
    this.writeIndex = new AtomicInteger(0);
  }

  /** 文件打开操作 */
  public void openFile() {
    try {
      this.writer = new FileWriter(this.getFileNameWritePath());
      this.bufferedWriter = new BufferedWriter(this.writer);
    } catch (IOException e) {
      e.printStackTrace();
    }
  }

  /**
   * 数据写入操作,不需添加换行符,所有在写入时统一添加换行符
   *
   * <p>目前采用最土办法,直接串行输出,以避免复杂的处理逻辑
   *
   * @param data 数据内容
   */
  public void writeLine(String data) throws IOException {
    String outData = data + Symbol.LINE;
    // 检查是否需要进行切换新文件
    if (this.checkSwitchFile(outData)) {
      // 切换到下一个文件
      nextFile();
    }

    // 数据写入操作
    bufferedWriter.write(outData);

    // 更新容量信息
    this.newSet(outData);
  }

  /**
   * 检查是否切换下一个文件
   *
   * @param data
   * @return
   */
  protected abstract boolean checkSwitchFile(String data);

  /**
   * 最新的数据设置
   *
   * @param data
   */
  protected abstract void newSet(String data);

  /** 进行当前标识的重置操作 */
  protected abstract void reset();

  /** 切换到下一个文件 */
  private void nextFile() {
    IOUtils.close(this.bufferedWriter);
    IOUtils.close(this.writer);

    String oldFilePath = getFileNameWritePath();
    String oldReName = getFileName();

    // 执行重命名旧文件
    FileUtils.rename(oldFilePath, oldReName);
    // 切换到下一文件
    this.writeIndex.incrementAndGet();
    // 在多线程并行时,使用比较交换解决并发问题

    // 标识重置操作
    this.reset();

    // 再次打开文件
    this.openFile();
  }

  /**
   * 获取当前正在写入的文件路径
   *
   * @return 文件名
   */
  private String getFileNameWritePath() {
    StringBuilder fileNameOut = new StringBuilder();
    fileNameOut.append(this.path);
    fileNameOut.append(Symbol.PATH);
    fileNameOut.append(getFileName());
    fileNameOut.append(WRITE_ING_FLAG);
    return fileNameOut.toString();
  }

  /**
   * 获取最终的文件名
   *
   * @return 文件名
   */
  private String getFileName() {
    StringBuilder fileNameOut = new StringBuilder();
    fileNameOut.append(this.fileName);
    fileNameOut.append(Symbol.MINUS);
    fileNameOut.append(writeIndex.get());
    fileNameOut.append(WRITE_FILE_SUFFIX_NAME);
    return fileNameOut.toString();
  }

  /** 文件关闭操作 */
  @Override
  public void close() {
    if (null != this.bufferedWriter) {
      IOUtils.close(this.bufferedWriter);
    }
    if (null != this.writer) {
      IOUtils.close(this.writer);
    }

    // 最终关闭时,进行文件重命名操作
    FileUtils.rename(getFileNameWritePath(), getFileName());
  }
}

按大小切分的类

/**
 * 按大小进行文件的切割
 *
 * @author liujun
 * @version 0.0.1
 */
public class ManyFileWriteSize extends AbstractManyFileWrite {

  /** 默认的文件大小32M */
  public static long DEFAULT_FILE_SIZE = 32 * 1024 * 1024;

  /** 切分的文件大小 */
  private final long spitFileSize;

  /** 当前文件大小 */
  private AtomicLong fileSize;

  /**
   * 使用默认的大小切换大小
   *
   * @param path
   * @param fileName
   */
  public ManyFileWriteSize(String path, String fileName) {
    this(path, fileName, DEFAULT_FILE_SIZE);
  }

  public ManyFileWriteSize(String path, String fileName, long spitFileSize) {
    super(path, fileName);
    this.spitFileSize = spitFileSize;
    this.fileSize = new AtomicLong(0);
  }

  @Override
  protected boolean checkSwitchFile(String data) {
    int dataLength = data.getBytes().length;
    return this.fileSize.get() + dataLength > spitFileSize;
  }

  @Override
  protected void newSet(String data) {
    int dataLength = data.getBytes().length;
    // 执行原子级的加法
    fileSize.addAndGet(dataLength);
  }

  @Override
  protected void reset() {
    this.fileSize.set(0);
  }
}

按行切分

/**
 * 按大小进行文件的切割
 *
 * @author liujun
 * @version 0.0.1
 */
public class ManyFileWriteSize extends AbstractManyFileWrite {

  /** 默认的文件大小32M */
  public static long DEFAULT_FILE_SIZE = 32 * 1024 * 1024;

  /** 切分的文件大小 */
  private final long spitFileSize;

  /** 当前文件大小 */
  private AtomicLong fileSize;

  /**
   * 使用默认的大小切换大小
   *
   * @param path
   * @param fileName
   */
  public ManyFileWriteSize(String path, String fileName) {
    this(path, fileName, DEFAULT_FILE_SIZE);
  }

  public ManyFileWriteSize(String path, String fileName, long spitFileSize) {
    super(path, fileName);
    this.spitFileSize = spitFileSize;
    this.fileSize = new AtomicLong(0);
  }

  @Override
  protected boolean checkSwitchFile(String data) {
    int dataLength = data.getBytes().length;
    return this.fileSize.get() + dataLength > spitFileSize;
  }

  @Override
  protected void newSet(String data) {
    int dataLength = data.getBytes().length;
    // 执行原子级的加法
    fileSize.addAndGet(dataLength);
  }

  @Override
  protected void reset() {
    this.fileSize.set(0);
  }
}

最后就是写义了两个工厂方法,用来获取按大小和按行切分的文件实例

/**
 * 文件写操作
 *
 * @author liujun
 * @version 0.0.1
 */
public class ManyFileWrite {

  /**
   * 按文件大小进行切分操作,使用默认大小32M
   *
   * @param path 路径
   * @param fileNme 文件名
   * @return 切分对象
   */
  public static AbstractManyFileWrite manyFileWriteBySize(String path, String fileNme) {
    return new ManyFileWriteSize(path, fileNme);
  }

  /**
   * 按文件按行进行切分操作,使用默认2万行
   *
   * @param path 路径
   * @param fileNme 文件名
   * @return 切分对象
   */
  public static AbstractManyFileWrite manyFileWriteByLine(String path, String fileNme) {
    return new ManyFileWriteLine(path, fileNme);
  }
}

读写调用

最后再来看下文件切分的调用吧:


  /** 去重的前的数据 */
  private static final String UNIQUE_DATA_OUT_PATH = "unique-data-before";

  /**
   * 执行文件的切分操作
   *
   * @param path 原始路径
   * @param spitOutPath 分隔后的路径
   */
  private void spitFile(String path, String spitOutPath) {
    try (ManyFileReader reader = new ManyFileReader(path);
         AbstractManyFileWrite write =
            ManyFileWrite.manyFileWriteBySize(spitOutPath, UNIQUE_DATA_OUT_PATH)) {

      reader.openFile();
      write.openFile();

      String line;
      while ((line = reader.readLine()) != null) {
        write.writeLine(line);
      }
    } catch (IOException e) {
      e.printStackTrace();
    }
  }

总结:

对于大型的多文件来说,读取并不复杂,重点在于文件名的排序、当前读取的文件索引,单文件读取结束时的文件切换,以及不要忘了实现AutoCloseable接口,只要做到这几点,多文件的连续读取就如同单文件一般顺滑。

对于大型的多文件写入来说,写入的逻辑同单文件,这个控制的重点在于,文件索引名中的索引号控制,单文件最大上限的控制。同样了不忘了实现AutoCloseable接口,做到这几点,多文件的连续写入,也如同写单文件一般。

如同我的实现一般。客户端在调用时,根本感知不到这是多文件的连续写入,感觉就是在使用JDK的IO流一样,只知道是在写文件,至于多大,何时做切换等一系的逻辑。客户端根本感知不到。

文件的切分就完成了,如果想查看更加详细的代码,可至我的github:

https://github.com/kkzfl22/datastruct/blob/master/src/main/java/com/liujun/datastruct/datacompare/bigfilecompare/uniquerows/UniqueRowProcess.java

下一节,我请继续分享超大文件对比的文件排序过程。

震惊!Redis+Spark组合竟能如此高效处理TB级数据 随着短视频、物联网等场景的爆发,企业每天要处理的TB级数据已从"偶尔发生"变成"日常刚需"。传统方案要么存储慢(如HDFS)、要么计算慢(如MapReduce)、要么实时性差(如关系型数据库)。本文聚焦"Redis+Spark"组合,覆盖从数据存储、计算到实时反馈的全流程,帮助开发者理解如何用这对组合解决超大规模数据处理的核心痛点。用"超市仓库+工厂流水线"的故事类比Redis和Spark拆解两者的核心能力与协同机制。 阅读详情

相关推荐

衡山派Luban-Lite系统SDIO无线网络配置实战:以D133CBV-QFN88开发板与RTL8189模组为例

本文详细介绍了在衡山派D133CBV-QFN88开发板上,为Luban-Lite系统配置SDIO无线网络的完整实战流程。通过配置SDMC接口、RTL8189 Wi-Fi驱动、lwIP协议栈及内核参数,并解决编译分区问题,最终实现Wi-Fi网络连接与测试,为嵌入式设备联网提供清晰指导。

weixin_35677363的博客 266

TB级别数据库恢复案例(从RAC到单机)

一、环境 从11.2.0.3RAC+ASM恢复至11.2.0.4单机环境 二、步骤 1.装载spfile spifle直接装载由于系统环境不同,可能导致无...

cuicuocui2297的博客 356

SECS/GEM协议库及开源代码

以下是在开发SECS/GEM协议过程中,在网络上搜集协议实现资源,希望对SECS/GEM协议感兴趣的同学能有所帮助。 开源代码 freesecs FREESECS 是一个开源的SEMI SECS协议库,采用C++语言实现,可运行于Linux, MacOS X, NetBSD。 实现协议:E37.1、E5 开源地址:freesecs download | SourceForge.net 下载地址:https://download.youkuaiyun.com/download/BT_LEO/24305429

码农的历程 9934

文本文件切割工具

在日常工作中,有时因平台限制或工作需要,需将一个大文件按行或文件大小分割成若干个小文件。本工具是基于行对大文本文件进行切割设计的,如需按文件大小切割,可根据大文件大小结合总行数大体估算下单文件大体行数,进行简单换算。 Maven项目引入 <dependency> <groupId>commons-io</groupId> <artifactId>commons-io</artifactId> <version...

caryeko的专栏 1373

道闸不自动落杆故障排查:从传感器原理到控制器调试全解析

在工业自动化和物联网系统中,传感器与控制器构成的闭环控制是保障设备可靠运行的核心。其基本原理是通过传感器采集环境状态,控制器依据预设逻辑做出决策并驱动执行器动作。这一技术价值在于实现了无人值守下的安全、高效自动化,广泛应用于智能交通、安防和智能楼宇等领域。以停车场道闸系统为例,其自动落杆功能高度依赖地感线圈与防砸雷达的协同。地感线圈作为触发单元,负责感知车辆接近;而防砸雷达则作为持续监测的安全单元,通过微波探测防砸区域内是否有障碍物,其信号是控制器执行落杆决策的关键依据。当系统出现车辆通过后闸杆不落的典型故

weixin_29190651的博客 309

使用protege推理小例子---关系链

使用protege推理小例子---关系链关系链推理 SubPropertityChain在Protege中使用关系链推理1、创建Person类2、创建对象关系3、添加实例4、进行推理5、推理结果 关系链推理 SubPropertityChain 关系链简单的说就是将多个关系表达式串联起来,如下图 1-1 图1-1 小明的父亲是大明,大明的父亲是老明。这就是一个由两组关系连接的关系链,根据关系链可以推理出,小明和老明之间的关系是爷孙关系。 在Protege中使用关系链推理 1、创建Person类 在Entit

weixin_45237780的博客 4457

动辄数百TB级数据的分析平台 海量并发无压力

作者简介:孔淼,诸葛io创始人/CEO连续创业者,毕业于华中科技大学,前37degree CTO。曾带领团队打造过脉搏网、知客数据等知名大数据平台,并服务中国电信、奥美、九阳集团等企业。2014年底,开始打造诸葛io。本文源自诸葛io创始人&amp;CEO孔淼在AWS技术峰会上的分享内容,从技术架构和底层平台方面讲解全量数据处理的分析平台如何实现。 责任编辑:孙浩峰 技术之路,一起进步,云计算...

科技峰行者的博客 2224

LDO参数解读、特性、参考设计

目录 一、工作原理 二、基本参数解释 三、LDO的一些特性 1、输出自放电 2、软启动 3、LDO效率 4、动态负载调整(∆VOUT) 5、线性瞬态响应 6、压差(Dropout Voltage) 四、参考设计 1、输入输出电容选择 2、Layout参考 一、工作原理 LDO是Low Dropout Regulator的缩写,意思是低压差线性稳压器,下面是LDO的内部框图,大致的工作原理就是:参考电压Vref和反馈电压FB(VOUT通过两个电阻分压)分别接在误差放大器的反向和正向

记得诚 1万+

单台机器上实现TB级的数据对比之数据排序

在单台机器上实现TB级的数据对比之数据排序 整体流程 在上一个章节已经实现了对大型文件的拆分.今天来继续分享关于数据的排序。 文件排序的逻辑不复杂。将数据读取进内存中然后排序。写入至磁盘中。由于这些文件相互完全不关联。可以并行化处理。那先还是看下整体的一个结构吧。 这个主要涉及到以下内容: 并行排序控制器,它的主要作用是控制向线程池中加入任务的数量。 线程池,用来执行当前的排序任务。 排序任务。将排序中涉及的到操作,封装到一个任务中。包括从文件中读取数据到内存,再将内存中的内容进行排序,最后再将排序后的

bug_null的博客 481

13、离散时间系统建模与分析

本文系统介绍了离散时间系统的建模与分析方法,涵盖连续时间模型的离散化过程、系统稳定性判断准则、输入输出模型转换方法以及有限脉冲响应和阶跃响应模型的应用。通过多个示例详细展示了不同系统在离散化过程中的特性变化,并探讨了采样间隔对系统动态特性的影响。此外,文章还分析了时间延迟的处理方法,并总结了关键知识点及操作步骤,为离散时间系统的实际应用提供了理论基础和实践指导。

2w3e4r5t6y的博客 188

EMB电子机械制动系统冗余备份方案介绍

随着汽车智能化技术的快速发展,自动驾驶技术的不断升级,对车辆制动系统的可靠性和安全性提出了更高要求。根据国际汽车安全法规(如UN R13-H)的最新修订,L3级及以上自动驾驶车辆必须配备具有冗余功能的制动系统,以确保在任何单一故障发生时仍能维持部分或全部制动能力。本文重点讨论最具前瞻性的EMB(电子机械制动)系统的冗余备份设计方案

m0_59012156的博客 853

单台机器上实现TB级的数据对比之数据合并

在单台机器上实现TB级的数据对比之数据合并 整体思路 在上一章节,我介绍了如何对切分后的数据进行并行排序,这节来到了最后的操作,数据的合并操作。将数据进行对比,找出添加的数据、修改的数据、删除的数据。需要特别处理下重复的数据。在第一章节我已经介绍了这个大致的思路,但未深入细节来讨论如何实现,这章将深入细节将数据合并的逻辑做一个完整的说明。 这个逻辑看着有点复杂吧,那我来详细的解释下吧! 在原始排序文件中读取所有文件的首行数据,并记录到以文件索引为下标的数组中。就叫它srcDataList 在目标排

bug_null的博客 497

RK3399外设驱动之MIPI

RK3399外设驱动之MIPI 文章目录RK3399外设驱动之MIPIMIPI命令解析入口代码mipi显示配置实例rk3399mipi驱动rk mipi驱动注册过程rk32_mipi_dsi.c解析 内核版本 Linux4.4 平台 rk3399 作者 nineyole MIPI命令解析入口代码 MIPI的入口代码如下:kernel\drivers\video\rockchip\screen\lcd_mipi.c static int __init rk_mipi_screen_in

学无止境 2227

在单台机器上实现TB级的数据对比

在单台机器上实现TB级的数据对比 前几天我在做公司项目的时候,需要对数据进行比较。数据量不大,也就几千条而已。当时功能完成后,我开始思考一个问题。就是当对比的文件是特别大的时候,我还能实现吗?那现在对问题做出假设: 问题: 现在有两个超大文件集,原始数据集和目标数据集,每个文件集中都有超过1亿的记录,数据中存在重复的记录,编写一个程序,可以找出两个数据集之间的差异,求解出三类数据: 原始数据集中存在,目标数据集中不存在,为待删除的数据记录。 原始数据集中存在,目标数据集中也存在,但内容不一致,为待修改的记录

bug_null的博客 418

Probability and Statistics - 4th edition

Probability and Statistics - 4th edition

ssm框架搭建

这个是一个在idea上成功跑起来的ssm框架项目,保存在这里方便以后使用直接下载

如何在单台8G内存机器上实现1TB日志排序?

问题: 最近在面试人的时候,我经常会问一个问题,题目如下: 现在有一批日志数据,大小为1TB,数据是某一天的生产的日志数据,现在只有一台单CPU及8G内存的机器,请使用算法对此日志数据按时间的先后顺序进行排序。 可面试了好多人,都没有回答出这个问题 针对这个问题今天来讲讲这个问题我的解法。 解决方案1:桶排序 它的原理是利用分区字段的特点,将数据分别写入到多个桶文件中...

bug_null的博客 3837

RU DOS版、EFI版32bit/64bit BIOS常用工具

DOS版、EFI版的RU工具,可用来查看IO、MEM、PCI、SMBIOS等资源。亲测在EFI SHELL下可用。

百TB级数据拷贝distcp性能调优

文章目录百TB级数据拷贝distcp性能调优背景拷贝方式速度问题启动慢同步慢收尾慢调优措施慢启动问题distcp参数调优数据倾斜问题慢节点问题机房带宽问题其它实际测试 百TB级数据拷贝distcp性能调优 背景 配合集群迁移,需要迁移6PB数据 迁移安排在当天天任务完成之后开启操作,9点-10点 需要在晚上17点之前完成当天增量数据迁移(5-8小时完成120TB数据同步) 拷贝方式 全量数据约6P...

weichanhua的博客 4889

华为的C语言编程规范.pdf

华为技术有限公司内部技术规范。本规范制定了编写C语言程序的基本原则、规则和建议。从代码的清晰、简洁、可测试、安全、程序效率、可移植各个方面对C语言编程作出了具体指导。

如何用Python脚本自动清洗TB级微调数据?一文讲透核心逻辑

高效解决TB级数据清洗难题,本文深入讲解大模型微调的数据清洗与格式转换(Python+Shell 自动化)的完整流程,涵盖去重、过滤、标准化及批量处理技巧,适用于大规模语料预处理场景。方法实用、可复用性强,值得收藏。

simcode的专栏 1051

单机TB级数据处理:从内存瓶颈到I/O优化的实战指南

海量数据处理并非天然属于分布式系统,当数据规模达到TB量级但尚未跨节点时,单机系统工程能力成为关键分水岭。其核心原理在于正视物理约束——内存容量、磁盘带宽、CPU缓存与系统调用开销共同构成性能天花板。技术价值体现在以最小硬件成本实现确定性高吞吐:通过分块流式读取规避OOM、二进制存储压缩50%+空间、Shell管道复用OS级外部排序等手段,显著超越通用脚本语言的默认行为。典型应用场景包括日志分析、传感器数据聚合、用户行为埋点清洗及基因序列预处理。本文聚焦真实生产中反复验证的单机优化路径,覆盖wget下载参数

rongdmmap的博客 466

Lightning导入单个TB级CSV文件加速方案

作者: cchouqiang 原文来源: https://tidb.net/blog/a193c892 ...

TiDB 社区干货传送门 483

TiDB:Lightning 导入 TB 级 CSV 文件加速秘籍

作者: cchouqiang 原文来源: https://tidb.net/blog/a193c892 ...

TiDB 社区干货传送门 559

【工业级点云处理秘籍】:3步实现TB级点云数据实时渲染

掌握TB级点云数据实时渲染秘诀,3步实现高效点云的可视化。适用于工业检测、数字孪生等场景,通过数据分块、LOD优化与GPU加速,显著提升渲染性能。方法实用,效果显著,值得收藏。

Instrustar的博客 1104

为什么 tosutil 比 cp 快一个数量级?——TB 级数据传输背后的工程原理

摘要:本文对比了挂载盘直接cp与tosutil工具在AI训练场景中的性能差异。挂载盘通过FUSE层转换导致单流串行传输、无容错机制,而tosutil通过API直连、分片并发、连接复用和断点续传四大核心机制,显著提升TB级数据及海量小文件的传输效率。建议日常小文件使用挂载盘,大规模数据传输优先选用tosutil以获得数量级的速度提升。

数据与算法架构提升之路专栏 449

数据库垂直切分迁移实战

原文链接:https://github.com/Elin-Zhou/develop-doc/blob/master/%E6%95%B0%E6%8D%AE%E5%BA%93%E5%9E%82%E7%9B%B4%E5%88%87%E5%88%86%E8%BF%81%E7%A7%BB.md 背景 原来的业务所有数据库都在一个实例上,配置为8C64G 1TB。由于业务快速增长,在业务高峰期时,数据库QPS...

夕下奕林的专栏 633

60TB 数据量的作业从 Hive 迁移到 Spark 在 Facebook 的实践

Facebook 经常使用分析来进行数据驱动的决策。在过去的几年里,用户和产品都得到了增长,使得我们分析引擎中单个查询的数据量达到了数十TB。我们的一些批处理分析都是基于 Hive 平台(Apache Hive 是 Facebook 在2009年贡献给社区的)和 Corona( Facebook 内部的 MapReduce 实现)进行的。Facebook 还针对包括 Hive 在内的多个内部数据存...

阿里云云栖号 1293

elasticsearch-优化方案-TB级数据

一 名词解释 集群:cluster,具有相同clusterName的节点组成的集群。 节点:node,相当于数据库中的db实例。 索引:index,相当于数据库database的概念,一个集群可以包含多个索引,一个索引包含多个分片(配置文件中配置)。 分片:shards,索引可以切分成多个分片,分布在不同的节点上,节点包含必须包含主分片,同时也可以存在一个或者多个副本,一个分片是一个底层的工作单元。它仅保存了全部数据中的一部分。一个分片可以是主分片或者副本分片。索引内任意一个文档都归属于一个主分片,所以

多年互联网一线运维开发经验,为多家企业独立开发过相关运维管理平台,负责过近千台服务器运维管理工作,对运维及运维开发岗位有深入理解。 2171
上一篇: 在单台机器上实现TB级的数据对比
下一篇: 单台机器上实现TB级的数据对比之数据排序
null_null_bug
博客等级 码龄7年 72粉丝 71原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值