当前位置: 首页 > news >正文

nodejs操作excel文件实例,读取sheets, 设置cell颜色

本代码是我帮客户做的兼职的实例,涉及用node读取excel文件,遍历sheets,给单元格设置颜色等操作,希望对大家接活有所帮助。

gen.js

 
let dir="Z:\\武汉烟厂\\山东区域\\备档资料\\销区零售终端APP维护清单\\走访档案\\2024年6月\\200户走访档案\\修改\\";
let dir2="Z:\\liujuan\\new_gen4\\";const fs = require('fs');
const path = require('path');
const ExcelJS = require('exceljs');// get text in cell
function gv(cell) {let v=cell.value; if(!v) return '';v = (v.richText? v.richText.map(({ text }) => text).join(''): v.toString());return v.trim().toLowerCase().replace(/[(]/g, '(').replace(/[)]/g, ')').replace(/\s/g, '');
}async function make_console(filename, sheetname, list)
{const FilePath = path.join(dir2, `console_${filename}_${sheetname}.js`);    const file_content=`
let sheet_name="${sheetname}";
let list=${list};
let diffs='', diffj=[]; let nl='\\r\\n';
let noinput=document.getElementById('licensenum');
function check_one(list, itemno) 
{ if(itemno>=list.length){ console.log(diffs); console.log(diffj); return; }console.log('checking '+itemno);let item=list[itemno]; let { no }=item; noinput.value=no; queryInfo(); setTimeout(()=>{let diff={no, cols:[]}; let pushed_diff=false;let tbody=document.getElementById('detailTbodyId'); if(!tbody || !tbody.children || tbody.children.length<1 || !tbody.children[0].children || tbody.children[0].children.length<4){ let msg='许可证不存在1: '+no; console.log(msg); diffs+=(msg+nl+nl); diffj.push(diff); check_one(list, itemno+1); return; }let tds=tbody.children[0].children; if(tds[0].innerText.toLowerCase().trim()!=no) { let msg='许可证不存在2: '+no; console.log(msg); diffs+=(msg+nl+nl); diffj.push(diff); check_one(list, itemno+1); return; }if(tds[1].innerText.toLowerCase().trim().replace(/[(]/g, '(').replace(/[)]/g, ')').replace(/\\s/g, '')!=item.company) { if(!pushed_diff) { pushed_diff=true; diffj.push(diff); } diff.cols.push('company'); diffs+=(no+': '+nl+tds[1].innerText+nl+item.company+nl+nl);}if(tds[2].innerText.toLowerCase().trim().replace(/[(]/g, '(').replace(/[)]/g, ')').replace(/\\s/g, '')!=item.addr) { if(!pushed_diff) { pushed_diff=true; diffj.push(diff); } diff.cols.push('addr'); diffs+=(no+': '+nl+tds[2].innerText+nl+item.addr+nl+nl);}if(!tds[3].innerText.toLowerCase().includes(item.date)) { if(!pushed_diff) { pushed_diff=true; diffj.push(diff); } diff.cols.push('date');  diffs+=(no+': '+nl+tds[3].innerText+nl+item.date+nl+nl);}check_one(list, itemno+1);}, 2000);  
}
check_one(list, 0);
`;fs.writeFileSync(FilePath, file_content);
}async function make_mark(filename, sheetname)
{const FilePath = path.join(dir2, `mark_${filename}_${sheetname}.js`);    const file_content=`
let diffs=
;
let filename='${filename}';
let sheet_name="${sheetname}";
let dir="${ dir.replace(/\\/g, "\\\\") }";
const ExcelJS = require('exceljs');
const fs = require('fs');let style_red={font:{color:{ argb: 'FFFF0000'}}};
let style_black={font:{color:{ argb: 'FF000000'}}};
let style_blue={font:{color:{ argb: 'FF0000FF'}}};
function gv(cell) {let v=cell.value; if(!v) return '';v = (v.richText? v.richText.map(({ text }) => text).join(''): v.toString());return v.trim().toLowerCase().replace(/[(]/g, '(').replace(/[)]/g, ')').replace(/\\s/g, '');
}async function ProcessSheet(sheet)
{let rows=sheet.rowCount, cols=sheet.columnCount;let found_first_row=false, no_col=0, addr_col=0, date_col=0, company_col=0, result=[];for(let row=1; row<=rows; row++){console.log('row: ', row);let r=sheet.getRow(row);if(found_first_row){let no_cell=r.getCell(no_col), no=gv(no_cell); if(!no){ for(let col=1; col<=cols; col++) r.getCell(col).style=style_black; continue; }let diff; if(diff=diffs.find(d=>d.no==no)){  let dcols=diff.cols;if(dcols.length==0) { for(let col=1; col<=cols; col++) r.getCell(col).style=style_black; no_cell.style=style_blue; continue;}for(let col=1; col<=cols; col++){let cell=r.getCell(col); if((company_col==col && dcols.includes('company'))||(addr_col==col && dcols.includes('addr'))||(date_col==col && dcols.includes('date'))) { cell.style=style_red; }else cell.style=style_black;} }else{  for(let col=1; col<=cols; col++) r.getCell(col).style=style_black;}}else{if(gv(r.getCell(1))=='区域' && gv(r.getCell(3))=='人员'){ // console.log('成功找到区域和人员列');for(let col=3; col<=cols; col++){let cell=r.getCell(col); let v=gv(cell);if(v=='专卖许可证名称') company_col=col;     else if(v=='地址') addr_col=col;     else if(v=='许可证到期日期') date_col=col;     else if(v=='编号') no_col=col;}if(company_col==0 || addr_col==0 || date_col==0 || no_col==0) {  console.log('未找到指定的4列'); return;  }else { found_first_row=true; console.log('成功找到指定的4列'); }}}} 
}async function ProcessFile(ExcelFilePath)
{const workbook = new ExcelJS.Workbook(); await workbook.xlsx.readFile(ExcelFilePath);let sheets=workbook.worksheets, sheetsCount=sheets.length;for(let sheet_index=0; sheet_index<sheetsCount; sheet_index++){let sheet=sheets[sheet_index]; if(sheet.name==sheet_name) { await ProcessSheet(sheet); break; }}await workbook.xlsx.writeFile(ExcelFilePath);
} 
ProcessFile(dir+filename+'.xlsx');
`;fs.writeFileSync(FilePath, file_content);
}async function traverseFolder(folderPath) {const items = fs.readdirSync(folderPath);for(let item of items){console.log(item);if(item.toLowerCase().includes(".xlsx") && item.indexOf("~")<0){const filename=item.substring(0, item.length-5); const ExcelFilePath = path.join(folderPath, item);      const workbook = new ExcelJS.Workbook(); await workbook.xlsx.readFile(ExcelFilePath);let sheets=workbook.worksheets, sheetsCount=sheets.length;for(let sheet_index=0; sheet_index<sheetsCount; sheet_index++){let sheet=sheets[sheet_index]; console.log(`sheet ${sheet.id}: ${sheet.name}`); //await ProcessSheet(sheet);let rows=sheet.rowCount, cols=sheet.columnCount; console.log(`${rows} rows, ${cols} cols`);let found_first_row=false, no_col=0, addr_col=0, date_col=0, company_col=0, result=[];for(let row=1; row<=rows; row++){let r=sheet.getRow(row);if(found_first_row){let no=gv(r.getCell(no_col)); if(!no) continue;result.push({no, addr: gv(r.getCell(addr_col)), company: gv(r.getCell(company_col)), date: gv(r.getCell(date_col)), });}else{if(gv(r.getCell(1))=='区域' && gv(r.getCell(3))=='人员'){ //console.log('成功找到区域和人员列');for(let col=3; col<=cols; col++){let cell=r.getCell(col); let v=gv(cell);if(v=='专卖许可证名称') company_col=col;     else if(v=='地址') addr_col=col;     else if(v=='许可证到期日期') date_col=col;     else if(v=='编号') no_col=col;               // console.log(`  [${row}, ${col}] ${v}`);}if(company_col==0 || addr_col==0 || date_col==0 || no_col==0) {  console.log('未找到指定的4列'); return;  }else { found_first_row=true; console.log('成功找到指定的4列'); }}}}//console.log(result.length, result[0]);try {await make_console(filename, sheet.name, JSON.stringify(result)); await make_mark(filename, sheet.name);fs.writeFileSync(`${dir2}${filename}_${sheet.name}_差异.txt`, '');} catch (err) {   console.error(err);  }}        }}
}traverseFolder(dir);

相关文章:

nodejs操作excel文件实例,读取sheets, 设置cell颜色

本代码是我帮客户做的兼职的实例&#xff0c;涉及用node读取excel文件&#xff0c;遍历sheets&#xff0c;给单元格设置颜色等操作&#xff0c;希望对大家接活有所帮助。 gen.js let dir"Z:\\武汉烟厂\\山东区域\\备档资料\\销区零售终端APP维护清单\\走访档案\\2024年6月…...

用GPT做足球预测案例分享

自从GPT出来后&#xff0c;一直想利用GPT的能力做点什么&#xff0c;想了很多项目&#xff0c;比如用GPT写小说&#xff0c;用GPT做股票分析&#xff0c;用GPT写营销文章&#xff0c;最终我选了一个比较有意思的方向&#xff1a;GPT足球预测。因为每天都有足球比赛&#xff0c;…...

代码随想录| 编辑距离

判断子序列[https://leetcode.cn/problems/is-subsequence/description/] 题意&#xff1a;给定字符串 s 和 t &#xff0c;判断 s 是否为 t 的子序列。 思路&#xff1a;从动态规划&#xff0c; dp[i][j] 表示s的前i-1个元素和t的前j-1个元素相同的子序列元素的个数。 还要对d…...

MOJO编程语言的编译与执行:深入编译器与解释器的工作原理

引言 MOJO编程语言以其面向对象的特性和简洁的语法而受到开发者的欢迎。在MOJO的世界中&#xff0c;编译器和解释器是两个核心组件&#xff0c;它们负责将MOJO代码转换为机器可执行的指令。本文将探讨MOJO编译器和解释器的工作原理&#xff0c;以及它们如何在MOJO编程过程中发…...

nginx-限制客户端并发数

文章目录 前言一、ngx_http_limit_conn_module二、指令介绍1. limit_conn_zone2.limit_conn3. limit_conn_log_level4. limit_conn_status 案例未限制限制 总结 前言 瞬时大量用户访问服务器&#xff0c;导致服务器超载而宕机。 恶意请求攻击服务器&#xff0c;导致服务器超载…...

Vatee万腾平台:智能生活的新选择

在科技飞速发展的今天&#xff0c;智能生活已经不再是遥不可及的梦想&#xff0c;而是逐渐渗透到我们日常生活的方方面面。Vatee万腾平台&#xff0c;作为智能科技领域的佼佼者&#xff0c;正以其创新的技术、丰富的应用场景和卓越的用户体验&#xff0c;成为智能生活的新选择&…...

白嫖A100-interLM大模型部署试用活动,亲测有效-2.Git

申明 以下部分内容来源于活动教学文档&#xff1a; Docs git 安装 是一个开源的分布式版本控制系统&#xff0c;被广泛用于软件协同开发。程序员的必备基础工具。 常用的 Git 操作 git init 初始化一个新的 Git 仓库&#xff0c;在当前目录创建一个 .git 隐藏文件夹来跟踪…...

LeetCode 60.排序排列(dfs暴力)

给出集合 [1,2,3,...,n]&#xff0c;其所有元素共有 n! 种排列。 按大小顺序列出所有排列情况&#xff0c;并一一标记&#xff0c;当 n 3 时, 所有排列如下&#xff1a; "123""132""213""231""312""321" 给定…...

矩阵分析与应用1-矩阵代数基础

矩阵分析与应用1-矩阵代数基础 1 矩阵的基本运算2 矩阵的初等变换3 向量空间、线性映射与Hilbert空间4 内积与范数5 随机向量6 矩阵的性能指标7 逆矩阵与伪逆矩阵8 Moore-Penrose逆矩阵9 矩阵的直和与Hadamard积10 Kronecker积与Khatri-Rao积11 向量化与矩阵化12 稀疏表示与压缩…...

Vue的学习之生命周期

一、生命周期 <!DOCTYPE html> <html><head><meta charset"utf-8"><title>Vue的学习</title><script src"vue.js" type"text/javascript" charset"utf-8"></script></head>&l…...

【MySQL】表的操作{创建/查看/修改/删除}

文章目录 1.创建表1.1comment&#xff1a;注释信息1.2存储引擎 2.查看表3.修改表3.1add添加列&#xff0c;对原数据无影响3.2drop删除列3.3modify修改列类型3.4change修改列名3.5rename [to]修改表名 4.删除表5.总结 1.创建表 CREATE TABLE table_name (field1 datatype,field…...

基于Python爬虫的城市二手房数据分析可视化

基于Python爬虫的城市二手房数据分析可视化 一、前言二、数据采集(爬虫,附完整代码)三、数据可视化(附完整代码)3.1 房源面积-总价散点图3.2 各行政区均价3.3 均价最高的10个小区3.4 均价最高的10个地段3.5 户型分布3.6 词云图四、如何更换城市一、前言 二手房具有价格普…...

这款新的 AI 语音助手击败了 OpenAI,成为 ChatGPT 最受期待的功能之一

OpenAI 推迟了 ChatGPT 令人印象深刻的语音模式&#xff0c;这让许多 AI 聊天机器人的粉丝感到不安&#xff0c;但他们现在可能已经被挖走了。法国人工智能开发商 Kyutai 推出了一款名为 Moshi 的实时语音 AI 助手。 Moshi 旨在通过语音&#xff08;如 Alexa 或 Google Assista…...

CTS单测某个模块和测试项

1 &#xff0c;测试单个模块命令 run cts -m <模块名> 比如&#xff1a;run cts -m CtsUsbTests模块名可以从测试报告中看&#xff0c;如下&#xff1a; 2&#xff0c; 测试单个测试项 run cts -m <模块名> -t <test_name> 比如&#xff1a;run cts -m ru…...

pytorch、pytorch_lightning、torchmetrics版本对应

目录 1.pytorch_lightning对应版本安装 2.PyTorch Lightning介绍 PyTorch Lightning 的作用&#xff1a; PyTorch Lightning 的基本用法&#xff1a; 报错&#xff1a;ModuleNotFoundError: No module named pytorch_lightning 这种报错一看就是缺了pytorch_lightning包&am…...

麒麟系统部署JeecgBoot

一、安装jdk 自带的即可&#xff0c;不必另外安装 二、安装MySQL 麒麟系统安装MySQL_麒麟系统安装万里数据库步骤-CSDN博客 三、安装Redis 麒麟系统安装Redis_麒麟上redis-CSDN博客 四、安装Nginx 1、下载 下载地址&#xff1a;https://redis.io/ 2、解压配置 tar .…...

要想贵人相助,首先自己得先成为贵人!

点击上方△腾阳 关注 转载请联系授权 在金庸江湖里&#xff0c;有两位大侠&#xff0c;一个是萧峰&#xff0c;一个是郭靖。 郭靖在《射雕英雄传》里是绝对的主角&#xff0c;在《神雕侠侣》当中也是重要的配角&#xff0c;甚至可以说是第二主角。 谈起郭靖&#xff0c;很多…...

使用块的网络 VGG

一、AlexNet与VGG 1、深度学习追求更深更大&#xff0c;使用VGG将卷积层组合为块 2、VGG块&#xff1a;3*3卷积&#xff08;pad1&#xff0c;n层&#xff0c;m通道&#xff09;、2*2最大池化层 二、VGG架构 1、多个VGG块后接全连接层 2、不同次数的重复块得到不同的架构&a…...

微信小程序性能与体验优化

1. 合理的设置可点击元素的响应区域大小&#xff1b; 比较常见的是页面的点击按钮太小&#xff0c;用户点击不到按钮&#xff0c;这样用户体验很不好。 2. 避免渲染页面耗时过长&#xff1b; 当页面渲染时间过长的话&#xff0c;会让用户感觉非常卡顿&#xff0c;当出现这种…...

Android14之获取包名/类名/服务名(二百二十三)

简介&#xff1a; CSDN博客专家&#xff0c;专注Android/Linux系统&#xff0c;分享多mic语音方案、音视频、编解码等技术&#xff0c;与大家一起成长&#xff01; 优质专栏&#xff1a;Audio工程师进阶系列【原创干货持续更新中……】&#x1f680; 优质专栏&#xff1a;多媒…...

内存分配函数malloc kmalloc vmalloc

内存分配函数malloc kmalloc vmalloc malloc实现步骤: 1)请求大小调整:首先,malloc 需要调整用户请求的大小,以适应内部数据结构(例如,可能需要存储额外的元数据)。通常,这包括对齐调整,确保分配的内存地址满足特定硬件要求(如对齐到8字节或16字节边界)。 2)空闲…...

Lombok 的 @Data 注解失效,未生成 getter/setter 方法引发的HTTP 406 错误

HTTP 状态码 406 (Not Acceptable) 和 500 (Internal Server Error) 是两类完全不同的错误&#xff0c;它们的含义、原因和解决方法都有显著区别。以下是详细对比&#xff1a; 1. HTTP 406 (Not Acceptable) 含义&#xff1a; 客户端请求的内容类型与服务器支持的内容类型不匹…...

Swift 协议扩展精进之路:解决 CoreData 托管实体子类的类型不匹配问题(下)

概述 在 Swift 开发语言中&#xff0c;各位秃头小码农们可以充分利用语法本身所带来的便利去劈荆斩棘。我们还可以恣意利用泛型、协议关联类型和协议扩展来进一步简化和优化我们复杂的代码需求。 不过&#xff0c;在涉及到多个子类派生于基类进行多态模拟的场景下&#xff0c;…...

什么是库存周转?如何用进销存系统提高库存周转率?

你可能听说过这样一句话&#xff1a; “利润不是赚出来的&#xff0c;是管出来的。” 尤其是在制造业、批发零售、电商这类“货堆成山”的行业&#xff0c;很多企业看着销售不错&#xff0c;账上却没钱、利润也不见了&#xff0c;一翻库存才发现&#xff1a; 一堆卖不动的旧货…...

el-switch文字内置

el-switch文字内置 效果 vue <div style"color:#ffffff;font-size:14px;float:left;margin-bottom:5px;margin-right:5px;">自动加载</div> <el-switch v-model"value" active-color"#3E99FB" inactive-color"#DCDFE6"…...

C++中string流知识详解和示例

一、概览与类体系 C 提供三种基于内存字符串的流&#xff0c;定义在 <sstream> 中&#xff1a; std::istringstream&#xff1a;输入流&#xff0c;从已有字符串中读取并解析。std::ostringstream&#xff1a;输出流&#xff0c;向内部缓冲区写入内容&#xff0c;最终取…...

leetcodeSQL解题:3564. 季节性销售分析

leetcodeSQL解题&#xff1a;3564. 季节性销售分析 题目&#xff1a; 表&#xff1a;sales ---------------------- | Column Name | Type | ---------------------- | sale_id | int | | product_id | int | | sale_date | date | | quantity | int | | price | decimal | -…...

使用 Streamlit 构建支持主流大模型与 Ollama 的轻量级统一平台

🎯 使用 Streamlit 构建支持主流大模型与 Ollama 的轻量级统一平台 📌 项目背景 随着大语言模型(LLM)的广泛应用,开发者常面临多个挑战: 各大模型(OpenAI、Claude、Gemini、Ollama)接口风格不统一;缺乏一个统一平台进行模型调用与测试;本地模型 Ollama 的集成与前…...

企业如何增强终端安全?

在数字化转型加速的今天&#xff0c;企业的业务运行越来越依赖于终端设备。从员工的笔记本电脑、智能手机&#xff0c;到工厂里的物联网设备、智能传感器&#xff0c;这些终端构成了企业与外部世界连接的 “神经末梢”。然而&#xff0c;随着远程办公的常态化和设备接入的爆炸式…...

OPENCV形态学基础之二腐蚀

一.腐蚀的原理 (图1) 数学表达式&#xff1a;dst(x,y) erode(src(x,y)) min(x,y)src(xx,yy) 腐蚀也是图像形态学的基本功能之一&#xff0c;腐蚀跟膨胀属于反向操作&#xff0c;膨胀是把图像图像变大&#xff0c;而腐蚀就是把图像变小。腐蚀后的图像变小变暗淡。 腐蚀…...