annotate src/sample/merge/TranslaterImp1.java @ 104:a2089a730a2e

change Translater class to interface.
author kent
date Sat, 22 Dec 2007 21:10:46 +0900
parents
children 2e649cd44078
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
104
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
1 package sample.merge;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
2
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
3 import java.util.ArrayList;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
4 import java.util.Collection;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
5 import java.util.LinkedList;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
6 import java.util.Stack;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
7
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
8 import remoteeditor.command.REPCommand;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
9 import remoteeditor.network.REP;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
10
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
11 public class TranslaterImp1 implements Translater{
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
12 //List <REPCommand> userList;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
13 //List <REPCommand> tokenList;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
14 private LinkedList<REPCommand> sentCmds;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
15 //private LinkedList<REPCommand> unMergedCmds;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
16 private Stack<REPCommand> unMergedCmds;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
17 public int eid;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
18
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
19 public TranslaterImp1(int _eid){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
20 eid = _eid;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
21 sentCmds = new LinkedList<REPCommand>();
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
22 unMergedCmds = new Stack<REPCommand>();
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
23 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
24
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
25 /**
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
26 * Translate cmd When the editor send REPCommand.
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
27 * but now, Only adding cmd to the queue is available.
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
28 * @param cmd
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
29 * @return translated command.
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
30 */
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
31 public REPCommand transSendCmd(REPCommand cmd){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
32 sentCmds.add(cmd);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
33 unMergedCmds.push(cmd);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
34 return cmd;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
35 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
36 /**
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
37 * Dequeue command cmd that was returned.
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
38 * @param cmd
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
39 */
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
40 public REPCommand[] catchOwnCommand(REPCommand cmd){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
41 ArrayList<REPCommand> returnCmds = new ArrayList<REPCommand>();
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
42 ArrayList<REPCommand> cmds = new ArrayList<REPCommand>();
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
43 // ringである以上、戻ってきたコマンドは確実にキューsentCmdsの先頭にある事を期待している
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
44 //REPCommand cmd0 = sentCmds.poll();
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
45 //assert cmd0.seq!=cmd.seq;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
46 assert cmd.eid==eid;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
47
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
48 /* スタックから全部取り出してマージする まだマージできないやつはまたスタックへ戻す */
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
49 while ( !unMergedCmds.isEmpty() ){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
50 REPCommand cmd0 = unMergedCmds.pop();
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
51 returnCmds.add( createUndo(cmd0) );
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
52 cmds.add(cmd0);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
53 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
54 //if (cmds.size()==0) return null;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
55 returnCmds.addAll( sortCmds(cmds) );
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
56 return returnCmds.toArray(new REPCommand[0]);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
57 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
58
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
59 private REPCommand createUndo(REPCommand cmd){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
60 //REPCommand retCmd = cmd.clone();
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
61 REPCommand retCmd = new REPCommand(cmd.cmd, cmd.sid, cmd.eid, cmd.seq, cmd.lineno, cmd.string.length(), cmd.string);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
62
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
63 if (cmd.cmd==REP.REPCMD_INSERT) retCmd.cmd=REP.REPCMD_DELETE;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
64 else if (cmd.cmd==REP.REPCMD_DELETE) retCmd.cmd=REP.REPCMD_INSERT;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
65 return retCmd;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
66 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
67
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
68 private ArrayList<REPCommand> sortCmds(ArrayList<REPCommand> cmds) {
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
69 ArrayList<REPCommand> sortedCmds = new ArrayList<REPCommand>();
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
70 REPCommand cmd0;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
71 int prevEid=0;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
72 int i,j;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
73
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
74 /* EID,SEQの低い順に、各EID毎に1個だけ選択しcmdsに格納 */
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
75 while ( null != (cmd0=getPrecedence(cmds, prevEid+1)) ){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
76 sortedCmds.add(cmd0);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
77 cmds.remove(cmd0);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
78 prevEid = cmd0.eid;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
79 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
80
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
81 /* lineno の大きい順にソート */
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
82 for (i=0; i<sortedCmds.size(); i++){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
83 int k=i;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
84 for (j=i+1; j<sortedCmds.size(); j++){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
85 if ( sortedCmds.get(k).lineno > sortedCmds.get(j).lineno ) continue;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
86 else if ( sortedCmds.get(k).lineno < sortedCmds.get(j).lineno
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
87 || sortedCmds.get(k).eid > sortedCmds.get(j).eid )
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
88 /* deleteとinsertの場合などはeidによらず、順序を強制する必要があるかも */
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
89 k=j;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
90 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
91 cmd0 = sortedCmds.get(i);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
92 sortedCmds.set(i, sortedCmds.get(k));
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
93 sortedCmds.set(k, cmd0);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
94 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
95 return sortedCmds;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
96 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
97
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
98 /* search cmd. ordering by min EID that is lower lowEid and min SEQ. */
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
99 private REPCommand getPrecedence(ArrayList<REPCommand> cmds, int lowEid) {
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
100 int cEid, cSeq;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
101 cEid=cSeq=Integer.MAX_VALUE;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
102 REPCommand ret=null;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
103 for (int i=0; i<cmds.size(); i++){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
104 REPCommand tmp = cmds.get(i);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
105 if ( tmp.eid<lowEid ) continue;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
106 else if ( tmp.eid>cEid ) continue;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
107 else if ( tmp.eid==cEid ) {
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
108 if ( tmp.seq>cSeq ) continue;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
109 cSeq=tmp.seq;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
110 ret = tmp;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
111 } else { /* tmp.eid<cEid */
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
112 cEid = tmp.eid;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
113 cSeq = tmp.seq;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
114 ret = tmp;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
115 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
116 //if ( cEid>cmds.get(i) && cmds.get(i)>lowEid )
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
117 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
118 return ret;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
119 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
120
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
121 /**
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
122 * Translate Command cmd that was received from SeMa.
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
123 * @param cmd the command to be translated.
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
124 * @return translated commannd.
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
125 */
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
126 public REPCommand[] transReceiveCmd(REPCommand cmd){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
127 int i=0;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
128 REPCommand cmds[];
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
129 if (cmd.eid==eid){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
130 return catchOwnCommand(cmd);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
131 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
132
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
133 for (REPCommand cmd0 : unMergedCmds){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
134 if (cmd0.eid==cmd.eid) i++;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
135 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
136
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
137 if ( sentCmds.size()<i ){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
138 cmds = new REPCommand[2];
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
139 String str = "NO OPERATION";
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
140 cmds[0] = new REPCommand(REP.REPCMD_NOP, 0, eid, 0, 0, str.length(), str);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
141 cmds[1] = cmd;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
142 //unMergedCmds.push(cmds[0]);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
143 unMergedCmds.push(cmd);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
144 sentCmds.add(cmds[0]);
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
145 return cmds;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
146 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
147
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
148 unMergedCmds.push(cmd); /* but.. */
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
149 cmds = new REPCommand[1];
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
150 cmds[0] = cmd;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
151 return cmds;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
152 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
153
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
154 public void setEid(int _eid){
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
155 eid = _eid;
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
156 }
a2089a730a2e change Translater class to interface.
kent
parents:
diff changeset
157 }