要对监控器中的数据成员进行访问,在考虑到多线程的情况下必须使用同步代码块来改变监控器中数据成员的值:
synchronized (mAdapterLocking) {
if (pEvery == 0) {
pEvery = pThisTime;
} else {
// 与上次平均时间进行平均.得到平均处理时间.
pEvery = (pEvery + pThisTime) / 2;
}
// 最长时间。
if (mMsgTimeMax < pThisTime) {
mMsgTimeMax = pThisTime;
}
mMsgCompleteCount++;
mMsgTimeEvery = pEvery;
mMsgBuffered--;
}
先new一个object对象,使用同步方式获得对象锁,在获得对象锁的权限后进程才有权限修改监控器中数据成员。
在监控器中不可修改的变量设置为public static final类型,这些变量在多线程的情况下不会被修改,但是其中的数据成员却可能在多个线程同时访问时在堆内存中被不同的线程修改掉。这时就出现线程读取数据错误的现象。所以必须对可能出现这种bug的数据成员的访问控制使用同步方式synchronized 。
二、在签到操作中的synchronized实现同步
签到操作是针对的操作员,不是每一笔不同的交易。只要该操作员在当天有一次签到操作,那么以后所有交易都会使用该次签到操作获得的令牌。
签到操作与网络传输中的令牌环网的机制是不同的,令牌环网中谁获得令牌谁就可以发送或者接受报文。但是在该业务中的签到操作只是为了标记在当天企业与银行有过交易操作。后续的操作不针对具体的某一笔交易和某一个人,即使是多个人相同的账号操作仍然获得的是相同的令牌。
签到方法:public synchronized String getSignToken() throws Exception{}因为该方法要访问数据成员。在应用中TBankxxx使用的是单例模式。在整个应用中只有一个实力。所以在多线程操作时实际上都是操作了一个对象。这样就应该使用同步处理。避免多个线程的数据混淆。给所有想获得令牌的线程排个队。只要有一个线程执行完成和目标行的签到交易,那么后续的线程都不用再次和目标行通信,直接使用第一个线程获得的令牌即可。