저는 Java3D로 작성된 CAD와 같은 도구와 결합 된 Swing으로 작성된 오래된 응용 프로그램의 유지 관리를 담당합니다. 메모리 사용에 문제가 있습니다. 프로파일 링 후에는 응용 프로그램의 실행 취소 기능과 관련이 있습니다.Swing/Java3D 애플리케이션의 상태 기반 실행 취소 : AOP 솔루션?
모든 기능을 실행 취소는이 같은 기본 개념으로, 상태 기반 :이 UndoActions을 만들 수
public class UndoAction {
private UndoTarget target;
private Object old_data;
private Object new_data;
}
코드는 기본적으로 응용 프로그램 전반에 걸쳐 산재 해있다. 새로운 객체, 기존 개체의 수정 및 하위 트리의 수정의 수정을 사이에 차이가 없기 때문에, 다음과 같은 상황이 발생합니다
- 새로운 객체
A
를 만듭니다무엇 발생하는 하나의 액션은 다음이다.
- 개체의
foo
필드를 수정하십시오. 새 UndoAction이 foo_old 및 foo_new가 포함 된 스택에 배치됩니다. - 개체의
bar
필드를 수정하십시오. 새 UndoAction이 스택에 배치되고 bar_old 및 bar_new가 포함됩니다. B.setField(A)
을 실행합니다. 스택에 새로운 UndoAction이 위치하는데, 여기에는 field_old와 field_new (== A)가 포함됩니다.
이것에 대한 세밀도 또는 제어가 전혀 없습니다. 이것은 유지 보수성을 전혀 도움이되지 않습니다.
이 시스템을 리팩터링하여 유지 보수가 가능하고 메모리 친화적이되도록하고 싶습니다. 안타깝게도 명령 패턴을 사용하여 실행 취소 시스템을 구현하는 것은 불가능합니다. 그 행동은 되돌리기에 너무 충격적이다. 다음을 구현하고 싶습니다.
- "경계선 실행 취소"를 제공하기 위해 주석을 사용하십시오. @Undoable()은 스택에 넣을 UndoAction을 생성하는 것으로 메소드를 표시합니다. 이것은 REQUIRE, NEST, JOIN ... 트랜잭션과 마찬가지로 매개 변수화 될 수 있습니다. Undoable 메소드를 입력하면 전체 객체 그래프가 복제됩니다.
- 트랜잭션 (= 메소드)이 끝나면 알고리즘은 새 상태를 이전 상태와 비교하고 diff를 저장해야합니다.
- 이것을 구현하려면 AOP를 사용할 수 있습니다. 이렇게하면 핵심 코드를 매우 깨끗하게 유지할 수 있습니다. 지금, 내 질문에
: 위의 세 기능 중 하나를 수행은 이미 자바에 존재 하는가? 나는 국가 기반 실행 취소 및 그와 관련된 문제들과 씨름을 제일 먼저하는 사람이 아니라는 것을 상상할 수 있습니다. (경계선 찾기 취소, 상태 비교, ...)
AspectJ는 매우 강력합니다. 이것은 당신이하고 싶은 일에 효과적 일 수 있습니다. – jbranchaud
'addFirst()'가 특정 한도를 초과 할 때 Deque와 removeLast()를 사용할 수 없습니까? – trashgod
UndoStack의 정확한 구현은 어렵지 않습니다. Swing UndoManager는 나를 위해이 작업을 잘 처리합니다. 어려운 점은 oldState와 newState를 생성하는 것입니다. 복제 할 항목, 새로운 UndoAction에 추가 할시기 및 이전 데이터가 어딘가에서 참조되지 않도록하는 방법입니다. – parasietje