EMMA Coverage Report (generated Sat Apr 29 12:52:00 BST 2006)
[all classes][net.sourceforge.pseudoq.solver]

COVERAGE SUMMARY FOR SOURCE FILE [ScanRowsStrategy.java]

nameclass, %method, %block, %line, %
ScanRowsStrategy.java100% (1/1)100% (7/7)83%  (275/331)91%  (42/46)

COVERAGE BREAKDOWN BY CLASS AND METHOD

nameclass, %method, %block, %line, %
     
class ScanRowsStrategy100% (1/1)100% (7/7)83%  (275/331)91%  (42/46)
counterValue (String): int 100% (1/1)44%  (11/25)75%  (3/4)
checkRow (int): SolutionStep 100% (1/1)68%  (39/57)86%  (6/7)
evaluate (): SolutionStep 100% (1/1)83%  (86/104)90%  (9/10)
checkBox (int, int): SolutionStep 100% (1/1)92%  (71/77)91%  (10/11)
<static initializer> 100% (1/1)100% (4/4)100% (1/1)
ScanRowsStrategy (int, int, int, int, Grid, Map, int, int, int): void 100% (1/1)100% (44/44)100% (12/12)
toString (): String 100% (1/1)100% (20/20)100% (1/1)

1/*
2 * Copyright (c) 2005 The PseudoQ Project.
3 *
4 * This file is part of PseudoQ.
5 *
6 * PseudoQ is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU Lesser General Public License as published by
8 * the Free Software Foundation; either version 2.1 of the License, or
9 * (at your option) any later version.
10 *
11 * PseudoQ is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 * GNU Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public License
17 * along with PseudoQ; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
19 */
20 
21package net.sourceforge.pseudoq.solver;
22 
23import java.util.Map;
24 
25import net.sourceforge.pseudoq.model.Coordinate;
26import net.sourceforge.pseudoq.model.Grid;
27 
28/**
29 * Puzzle-solving strategy that checks a super-row for values which are only
30 * missing from one row.  If so, this restricts the possibilities to one box,
31 * which is checked to see if it has only one unknown cell in that row.
32 * @author <a href="http://sourceforge.net/users/stevensa">Andrew Stevens</a>
33 */
34public class ScanRowsStrategy implements Strategy {
35    /** Log4J logger */
36    private static final org.apache.log4j.Logger log =
37            org.apache.log4j.LogManager.getLogger(ScanRowsStrategy.class);
38 
39    private int superRow;
40    private int value;
41    private int startRow;
42    private int endRow;
43    private Grid grid;
44    protected Map<String, Counter> counters;
45    private int startBox;
46    private int endBox;
47    private int cellsPerBox;
48 
49    /** Creates a new instance of ScanRowsStrategy */
50    public ScanRowsStrategy(int superRow, int value, int startRow, int endRow,
51            Grid grid, Map<String, Counter> counters, int startBox, int endBox, int cellsPerBox) {
52        log.debug("Initialising ScanRowsStrategy for value " + value + " on SuperRow " + superRow);
53        this.superRow = superRow;
54        this.value = value;
55        this.startRow = startRow;
56        this.endRow = endRow;
57        this.grid = grid;
58        this.counters = counters;
59        this.startBox = startBox;
60        this.endBox = endBox;
61        this.cellsPerBox = cellsPerBox;
62    }
63 
64    public SolutionStep evaluate()
65    throws ObsoleteStrategyException, UnsolveablePuzzleException
66    {
67        SolutionStep nextStep = null;
68 
69        if (counterValue("superRowIndicatorCount-" + superRow + "-" + value) ==
70                (endRow - startRow + 1)) {
71            throw new ObsoleteStrategyException("SuperRow contains all occurrences of value");
72        } else if (counterValue("superRowIndicatorCount-" + superRow + "-" + value) ==
73                (endRow - startRow)) {
74            // find row that doesn't contain the value
75            for (int row = startRow; row <= endRow; row++) {
76                if (counterValue("rowIndicatorCount-" + row + "-" + value) == 0) {
77                    if (nextStep != null) {
78                        throw new IllegalStateException("Counter out sync with grid for super-row " +
79                                superRow + ", value " + value);
80                    }
81                    nextStep = checkRow(row);
82                }
83            }
84 
85//            if ((counterValue("boxIndicatorCount-" + (2 * superRow) + "-" + value) +
86//                    counterValue("boxIndicatorCount-" + ((2 * superRow) + 1) + "-" + value)) != 1) {
87//                throw new IllegalStateException("Counters out of sync for super-row " +
88//                        superRow + " boxes, value " + value);
89//            }
90 
91//            if (counterValue("rowIndicatorCount-" + row1 + "-" + value) == 0 &&
92//                    counterValue("rowIndicatorCount-" + row2 + "-" + value) == 1) {
93//                nextStep = checkRow(row1);
94//            } else if (counterValue("rowIndicatorCount-" + row1 + "-" + value) == 1 &&
95//                    counterValue("rowIndicatorCount-" + row2 + "-" + value) == 0) {
96//                nextStep = checkRow(row2);
97//            } else {
98//                throw new IllegalStateException("Counter out sync with grid for super-row " +
99//                        superRow + ", value " + value);
100//            }
101        }
102 
103        return nextStep;
104    }
105 
106    private int counterValue(String counterKey) {
107        Counter counter = counters.get(counterKey);
108        if (counter == null) {
109            throw new IllegalStateException("Counter " + counterKey + " not found.");
110        } else {
111            return counter.getCount();
112        }
113    }
114 
115    private SolutionStep checkRow(int row)
116    throws UnsolveablePuzzleException
117    {
118        SolutionStep nextStep = null;
119        
120        // find box that doesn't contain the value
121        for (int box = startBox; box <= endBox; box += 1) {
122            if (counterValue("boxIndicatorCount-" + box + "-" + value) == 0) {
123                if (nextStep != null) {
124                    throw new IllegalStateException("Counters out of sync for super-row " +
125                            superRow + " boxes, value " + value);
126                }
127                nextStep = checkBox(row, box - startBox);
128            }
129        }
130//        if (counterValue("boxIndicatorCount-" + (2 * superRow) + "-" + value) == 1) {
131//            return checkBox(row, 1);
132//        } else {
133//            return checkBox(row, 0);
134//        }
135 
136        return nextStep;
137    }
138 
139    private SolutionStep checkBox(int row, int superColumn)
140    throws UnsolveablePuzzleException
141    {
142        SolutionStep nextStep = null;
143        int possibles = 0;
144 
145        for (int column = cellsPerBox * superColumn; column < cellsPerBox * (superColumn + 1); column++) {
146            if (grid.get(new Coordinate(row, column)).equals(Integer.valueOf(0)) &&
147                    counterValue("columnIndicatorCount-" + column + "-" + value) == 0) {
148                nextStep = new SolutionStep(new Coordinate(row, column),
149                        value, this.toString());
150                possibles++;
151            }
152        }
153        if (possibles == 0) {
154            throw new UnsolveablePuzzleException(this.toString());
155        } else if (possibles > 1) {
156            nextStep = null;
157        }
158 
159        return nextStep;
160    }
161 
162    public String toString() {
163        return "ScanRows " + startRow + "-" + endRow + " for " + value;
164    }
165 
166}

[all classes][net.sourceforge.pseudoq.solver]
EMMA 2.0.5312 (C) Vladimir Roubtsov