|
本帖最后由 chenwq 于 2012-4-23 14:11 编辑
问题描述:
针对,D3C串行执行分类器训练模型的改进,
提出了多线程化分类器训练过程方案。
如图,首先,在主线程Main函数中,开启多个线程用于各个分类器训练(D3C的Test包含20个分类器),以及一个
线程监听程序,每隔固定时间,监测每个分类器是否训练完成,此外还用于分类器训练时间超过D3C设定的
训练时间时,移除该超时分类器线程。
全部分类器训练结束后者被移除之后,主线程被唤醒,继续执行D3C的后续操作。
分类器训练超时,杀死进程的实现:
对超时的分类器训练线程,采用interrupt()方法,将其中断。
- long t2 = System.currentTimeMillis();
- Calendar c = Calendar.getInstance();
- c.setTimeInMillis(t2 - startTime);
- if (c.get(Calendar.SECOND) >= terminateTime) {
- Logger.info(InitClassifiers.classifiersName[array.get(i).getI()] + " is removed!");
- // array.get(i).stop();
- // array.set(i, null);
- array.get(i).interrupt();
- array.remove(i);// 将已经完成的线程对象从队列中移除
- }
复制代码 之后,对应分类器线程的run()方法里面,检查,该线程是否被中断,
如果中断,则对其分类结果(以ArrayList保存)重新赋值,50%正确分类,50%分类失败
- public void run() {
- SelectiveEnsemble se = new SelectiveEnsemble();
-
- this.list[[this.i] = se.CrossValidationModel(input, classifier, numfolds,
- correctRateArray, random, this.i, this.qqs);
- if(Thread.interrupted()){
- System.out.println("-----------------------------------------------------");
- List<Integer> tmpLst = new ArrayList<Integer>();
-
- // for(int iii = 0; iii < this.list[this.i].size(); iii++){
- // if(iii % 2 == 0)
- // tmpLst.add(1);
- // else
- // tmpLst.add(0);
- // }
- this.list[this.i] = tmpLst;
- this.isFinished = true;
- }
- for (int j = 0; j < this.list[this.i].size(); j++) {
- if (this.list[this.i].get(j) == 0) {
- this.classifyErrorNo[this.i].add(j);
- }
- }
- this.isFinished = true;
- executeTime = System.currentTimeMillis();
- }
复制代码 因为Java里面的参数以引用的方式传递,如果,不对上述分类器的分类结果进行重新赋值,存在着部分分类结果存入ArrayList,即上述代码中的this.list[this.i],
而部分没有存入,或者,甚至,整个结果都在被中断的过程中被清除,这样分类的结果在后续的聚类、差异性度量中将无法引用,
导致程序异常。
如果能把被移除的分类器的输出结果的重新赋值过程去掉,整个逻辑将更加清楚,代码也将不带臭味。
如果有好的办法,请大家踊跃提啊!
参考:
Why Are Thread.stop, Thread.suspend, Thread.resume and Runtime.runFinalizersOnExit Deprecated?
How to Stop a Thread or a Task[ |
本帖子中包含更多资源
您需要 登录 才可以下载或查看,没有帐号?注册
x
|