现在有61个文件夹,每个文件夹下面有365个txt文件,每个txt文件里面的数据格式都是固定的,大约每个文件有700行数据左右。用什么方法把这几千万条数据导入到数据库中效率会高点优先要求效率...
求大牛给出思路
求大牛给出思路
解决方案 »
- 不使用frameset标签如何实现一个页面包含两个窗体?
- index.jsp通过模拟action接口 转发 到login.jsp页面后,页面背景无法显示
- 点击删除命令,然后点取消,但是还是删除掉了?---已上代码,如何解决?
- 大的软件项目用hibernate吗?
- getCurrentSession() 的怪现象 求助
- JSP菜鸟提个问题讨论:像PCONLINE这类的大型网站是怎样管理的(技术上)?
- 插入时间不知道是不是相等
- 处理页面请求时,访问业务层对象的机制?
- 这应该算是跨域问题吧?
- Session的怪问题。
- 求CRM项目全套静态页面(美工页面)
- 在Https页面中,如果iframe所引入页面是非https协议的页面弹出警告,请问怎么解决。
for(365个文件){
for(700行数据){
// sql生成
preparedstatment.addBatch();
}
// 一次连接数据库执行700条数据
preparedstatment.executeBatch();
}
}
最小颗粒度至少是一个txt文件
转化成json或者其他结构化语言保存?
或者保存文件只是保存文件索引,然后每次请求都是根据索引请求文件内容。
这样读取效率又低了。仅是个人想法,还请技术大牛点评
在Action里面处理多线程?!不推荐!对于此类大规模数据处理,建议的做法是,Web应用服务只负责接受请求(或者说指令)。另外写批处理程序负责批量的任务处理。这样结构灵活,且整体任务过程容易控制好。
另外,看楼主的意思有点打算用多线程来处理了,顺便再给点关注点和建议吧。
关注点:
◎ 批处理中比较讨厌的是重复发起任务,所以需要有标志控制;
◎ 既然是多线程,实际上就存在任务分配的问题,那么任务竞争与失败任务重做等也将成为问题;
◎ 多线程不是你启动线程数越多,速度就越快的,因为最终瓶颈点都在数据库的那张表上,所以线程数量太高将导致资源竞争激烈;
◎ 数据库表建议先删除或禁用所有索引,然后再执行批量插入,完毕后重建索引;
建议:
◎ 建议批处理程序分为两个部分:1、任务分配者;2、任务控制器;2、工作线程。
◎ 任务分配者,负责将整体任务切分为子任务,比如按照目录和文件生成任务项,在你的例子里是61×365个任务项,将任务项批量写入任务表;可以按目录循环,每次写入365个任务(行);需要注意的是,这个动作每个整体任务来时只能做一次,否则就重复了;
◎ 任务控制器:负责从数据库抓取任务、维护任务标志位、线程池和线程调度,包括任务重试机制;
◎ 工作线程:负责根据任务控制器传递过来的任务项,打开指定文件,读取数据,然后用batch做数据提交,一次性完成一个txt的处理;
◎ 在这种模式下,可以随时监控总体任务进度,而且可以随时停止任务进行,并随时继续开始执行任务。最后就是线程池的线程数配置问题了,这个看服务器压力问题。如果你数据库非常强劲,但客户机不行。可以在多台机器上启动任务控制器。
比如MYSQL,构造XXX.sql文件,再用导入
我当时的数据是几亿条数据,建议你用脚本调数据库load工具吧,吃不了多少内存。
我认为效率高点的还是格式化一下txt中的数据。。直接将txt的数据通过oracle命令映射插入表你那么多文件。。数据量那么大。。在应用中,无论怎么优化。。都没有直接使用命令行效率高。。直接和oracle性能挂钩。。少一个环节具体做法:例子:1. 创建测试表
create table test_import
(
id int primary key,
name varchar2(50),
age int,
test_null varchar2(20),
re varchar2(100)
);2. 创建imTable.ctl文件
load data infile 'f:/test.txt' append into table test_import
trailing nullcols
(
id terminated by ',', --字段
name terminated by ',', --字段
age terminated by ',', --字段
re terminated by ',' --字段
);3. 创建test.txt文件
test.txt
1,t1,20,第一个测试
2,t2,25,第二个测试
3,t3,22,第三个测试
4,t4,30,第四个测试
5,t5,28,第五个测试
6,t6,23,第六个测试4. sqlplus中sql导入语句
sqlldr 用户/密码@数据库实例名 control='f:/imTable.ctl' log='f:/log.txt' bad='f:/bad.txt' 5. 完成。。查看日志log.txt..
然后用下楼上的方法。不知道这样速度是不是快一点。
直接用程序导入数据库的确很慢,一千多万条数据大概得花5个小时,所以还是打算放弃这种方法。
可是有几千个文件,我不可能这样写:
infile a.csv
infile b.csv
...
...
...
有米有更简单点的方法
另,如果需要排序调整可以再次编写程序调整。
使用sqlldr导入