자바 - BlockingQueue 사용
6554 단어 BlockingQueue
최근 프로젝트 에 서 는 로그 파일 에서 파 라 메 터 를 가 져 온 다음 서로 다른 API 를 호출 하여 결 과 를 비교 해 야 합 니 다.하지만 어떤 방식 이 좋 을 지 몰라 jdk 의 매 뉴 얼 을 찾 아 보 니 BlockingQueue 라 는 좋 은 물건 을 발견 했다.
BlockingQueue 에 대한 소 개 는 관심 있 으 시 면 직접 보 세 요.http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/LinkedBlockingQueue.html
수 요 는 간단 합 니 다. Queue 에 파 라 메 터 를 넣 고 다음 전략 으로 소비 하 는 것 입 니 다.처음에는 서로 다른 스 레 드 를 통 해 대기 열 에 데 이 터 를 저장 한 다음 다음 서비스 에 BlockingQueue 의 대상 으로 돌아 갑 니 다. 다음 정책 은 대기 열 에서 소비 합 니 다. code 는 다음 과 같 습 니 다.
@SuppressWarnings("rawtypes")
@Override
public BlockingQueue getTxtLogContent(String path) {
File file = new File(path);
BufferedReader reader = null;
String tempStr = null;
final BlockingQueue queue = new LinkedBlockingQueue();
try {
reader = new BufferedReader(new FileReader(file));
while ((tempStr = reader.readLine()) != null) {
final InputOutputPrameters parameter = new InputOutputPrameters();
String[] list = tempStr.split(";");
if (list != null && list.length > 0) {
parameter.setInputParamters(list[0]);
parameter.setOutputParameters(list[1]);
}
new Thread(){
@SuppressWarnings("unchecked")
public void run(){
try {
Thread.sleep((long)(Math.random()*100));
log.info(" !");
queue.put(parameter);
log.info(" , " + queue.size() +" ! :"+ parameter.getInputParamters() + ";
:" + parameter.getOutputParameters());
} catch (Exception e) {
log.error(" :" + e);
}
}
}.start();
}
reader.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}finally {
if (reader != null) {
try {
reader.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
return queue;
}
그러나 실제 실행 할 때 로그 가 비교적 크기 때문에 다음 전략 은 1hour 또는 더 긴 시간 을 기 다 려 야 처리 할 수 있 습 니 다. 이것 은 요구 에 부합 되 지 않 습 니 다. 그래서 최적화 되 었 습 니 다. BlockingQueue 를 전체 static 로 바 꾼 다음 전략 은 이 대기 열 에 값 이 있 는 지, 값 이 있 으 면 소비 하 는 지 직접 감시 할 수 있 습 니 다.값 이 없 으 면 스 레 드 대기 나 시간 초과 등 다른 처 리 를 막 습 니 다.
개 선 된 code:
1. 새 대기 열 클래스:
public class ParameterQueue extends LinkedBlockingQueue<InputOutputPrameters> {
/**
*@Fields serialVersionUID:
*/
private static final long serialVersionUID = 6032356446145302484L;
private static BlockingQueue<InputOutputPrameters> queue = new LinkedBlockingQueue<InputOutputPrameters>();
/**
* @Fields log:
*/
private static final Logger log = LoggerFactory
.getLogger(ParameterQueue.class);
/**
*
* @Method:getParameter
* @Description:
* @return
*/
public static InputOutputPrameters getParameter(){
InputOutputPrameters result = null;
try {
result = (InputOutputPrameters)queue.take();
} catch (Exception e) {
log.error(" , :" + e);
}
return result;
}
/**
*
* @Method:getQueueSize
* @Description:
* @return
*/
public static Integer getQueueSize() {
return queue.size();
}
/**
*
* @Method:putParameter
* @Description:
* @param parameter
*/
public static void putParameter(InputOutputPrameters parameter) {
try {
queue.put(parameter);
} catch (Exception e) {
log.error(" , :" + e);
}
}
}
2. 파일 을 읽 을 때 이 대기 열 을 직접 조작 하여 대기 열 에 put 값 을 넣 습 니 다. 다음 정책 은 이 대기 열 에서 get 값 을 얻 습 니 다. put 의 code 는 다음 과 같 습 니 다.
public void getSource(String path) {
try {
File file = new File(path);
BufferedReader reader = null;
String tempStr = null;
try {
reader = new BufferedReader(new FileReader(file));
while ((tempStr = reader.readLine()) != null) {
final InputOutputPrameters parameter = new InputOutputPrameters();
String[] list = tempStr.split(";");
if (list != null && list.length > 0) {
parameter.setInputParamters(list[0]);
parameter.setOutputParameters(list[1]);
}
putInQueue(parameter);
}
reader.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}finally {
if (reader != null) {
try {
reader.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
} catch (Exception e) {
log.error(" : " + e);
}
}
/**
*
* @Method:putInQueue
* @Description:
* @param parameter
*/
private void putInQueue(final InputOutputPrameters parameter) {
new Thread(){
public void run(){
try {
Thread.sleep((long)(Math.random()*100));
log.info(" !");
ParameterQueue.putParameter(parameter);
log.info(" , " + ParameterQueue.getQueueSize() +" ! :"+ parameter.getInputParamters() + ";
:" + parameter.getOutputParameters());
} catch (Exception e) {
log.error(" :" + e);
}
}
}.start();
}
그래서 이 요 구 는 이 루어 졌 다.이 작은 수 요 를 기록 하면 나중에 찾 아 볼 수 있 습 니 다.
요약 하면 BlockingQueue 는 스 레 드 가 안전 하고 Array BlockingQueue, LinkedBlockingQueue 를 자주 사용 합 니 다.
Array BlockingQueue 는 용량 을 정 해 야 하 며, LinkedBlockingQueue 는 필요 하지 않 습 니 다.
동시에 소비 할 때 take () 는 스 레 드 를 막 을 수 있 습 니 다. 단일 스 레 드 가 달 릴 때 take () 가 도착 하지 않 으 면 전체 스 레 드 가 끊 깁 니 다.
그래서 구체 적 인 환경 수 요 를 보면 take 를 사용 하 는 지 다른 것 을 사용 하 는 지 저 는 보통 poll 을 사용 합 니 다. 시간 초과 시간 을 정할 수 있 기 때 문 입 니 다.
아, 어떻게 썼 는 지 모 르 겠 어 요. 이렇게 하 세 요.
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
PriorityBlockingQueue 우선 순위 규칙Priority BlockingQueue에 저장된 대상은Comparable 인터페이스를 실현하는 것이어야 합니다.대기열은 이 인터페이스의compare 방법을 통해 대상의priority를 확정합니다. 규칙은: 현재 다...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.