package no.uio.ifi.refaktor.benchmark;
+import java.util.LinkedList;
+import java.util.List;
+
import no.uio.ifi.refaktor.analyze.ExtractAndMoveMethodAnalysisResult;
import no.uio.ifi.refaktor.analyze.FavorNoUnfixesAnalysisResultComparator;
import no.uio.ifi.refaktor.analyze.NoTargetFoundException;
public class ProjectWideSearchBasedExtractAndMoveMethodAnalyzer {
private final IProject project;
+ private final List<ExtractAndMoveMethodAnalysisResult> results;
private int methodCount;
private long analysisStart;
public ProjectWideSearchBasedExtractAndMoveMethodAnalyzer(IProject project) {
this.project = project;
+ results = new LinkedList<ExtractAndMoveMethodAnalysisResult>();
methodCount = 0;
}
} catch (JavaModelException e) {
throw new RuntimeException(e);
} finally {
- RefaktorDebug.println("Time used on analysis: " + timeSinceAnalysisStart());
- RefaktorDebug.println("\n" + methodCount + " methods analyzed");
+ debugPrintFinalStatistics();
}
}
+ private void debugPrintFinalStatistics() {
+ for (ExtractAndMoveMethodAnalysisResult result: results)
+ RefaktorDebug.println(result);
+
+ RefaktorDebug.println("Number of results: " + results.size());
+ RefaktorDebug.println("Time used on analysis: " + timeSinceAnalysisStart());
+ RefaktorDebug.println(methodCount + " methods analyzed");
+ }
+
private void analyzeMethodsInPackage(IPackageFragment packageFragment) throws JavaModelException {
for (ICompilationUnit compilationUnit: packageFragment.getCompilationUnits())
analyzeMethodsInCompilationUnit(compilationUnit);
}
analyzer = new SearchBasedExtractAndMoveMethodAnalyzer(method, new FavorNoUnfixesAnalysisResultComparator());
analyzer.analyze();
- ExtractAndMoveMethodAnalysisResult result = analyzer.getResult();
- RefaktorDebug.println(result);
+ results.add(analyzer.getResult());
} catch (NoTargetFoundException e) {
- RefaktorDebug.println("No target found for " + method + "\n(" + analyzer.getNumberOfStatementsAnalyzed() + " statements analyzed)");
+// RefaktorDebug.println("No target found for " + method + "\n(" + analyzer.getNumberOfStatementsAnalyzed() + " statements analyzed)");
}
}
package no.uio.ifi.refaktor.analyze;
+import static no.uio.ifi.refaktor.RefaktorAssert.assertThat;
+import static org.hamcrest.CoreMatchers.notNullValue;
import no.uio.ifi.refaktor.prefix.Prefix;
import no.uio.ifi.refaktor.prefix.PrefixSet;
import no.uio.ifi.refaktor.utils.CompilationUnitTextSelection;
import org.eclipse.jdt.core.IMethod;
import org.eclipse.jdt.core.dom.IBinding;
+import org.eclipse.jdt.core.dom.IVariableBinding;
public class ExtractAndMoveMethodAnalysisResult {
+ private class ResultDataCalculator {
+ private final ExtractAndMoveMethodAnalyzer analyzer;
+
+ public ResultDataCalculator(ExtractAndMoveMethodAnalyzer analyzer) {
+ this.analyzer = analyzer;
+ }
+
+ public boolean hasMoreThanOnePossibleTarget() {
+ PrefixSet safePrefixes = analyzer.calculateSafePrefixes();
+ IBinding binding = safePrefixes.toList().getFirst().getVariableBindingOfFirstExpression();
+ for (Prefix prefix: safePrefixes) {
+ if (!prefix.getVariableBindingOfFirstExpression().isEqualTo(binding))
+ return true;
+ }
+ return false;
+ }
+
+ public int getTargetFrequency() {
+ if (hasMoreThanOnePossibleTarget())
+ ; // TODO: throw exception?
+ return analyzer.calculateMostFrequentPrefix().getCount();
+ }
+
+ public boolean hasNoUnfixes() {
+ return analyzer.getUnfixes().isEmpty();
+ }
+
+ public String calculateOriginalTargetKey() {
+ return analyzer.calculateOriginalTarget().getKey();
+ }
+ }
+
public final CompilationUnitTextSelection textSelection;
public final int numberOfStatementsAnalyzed;
public final int numberOfTextSelectionsAnalyzed;
public final IMethod method;
- private final ExtractAndMoveMethodAnalyzer analyzer;
+ private final boolean hasMoreThanOnePossibleTarget;
+ private final int targetFrequency;
+ private final boolean hasNoUnfixes;
+ private final String originalTargetKey;
public ExtractAndMoveMethodAnalysisResult(IMethod method, ExtractAndMoveMethodAnalyzer analyzer, CompilationUnitTextSelection textSelection, int numberOfStatementsAnalyzed, int numberOfTextSelectionsAnalyzed) {
this.method = method;
- this.analyzer = analyzer;
this.textSelection = textSelection;
this.numberOfStatementsAnalyzed = numberOfStatementsAnalyzed;
this.numberOfTextSelectionsAnalyzed = numberOfTextSelectionsAnalyzed;
+
+ ResultDataCalculator calculator = new ResultDataCalculator(analyzer);
+ hasMoreThanOnePossibleTarget = calculator.hasMoreThanOnePossibleTarget();
+ targetFrequency = calculator.getTargetFrequency();
+ hasNoUnfixes = calculator.hasNoUnfixes();
+ originalTargetKey = calculator.calculateOriginalTargetKey();
+
+ dropExpensiveCachedData();
+ }
+
+ private void dropExpensiveCachedData() {
+ textSelection.dropCachedData();
}
public boolean hasMoreThanOnePossibleTarget() {
- PrefixSet safePrefixes = analyzer.calculateSafePrefixes();
- IBinding binding = safePrefixes.toList().getFirst().getVariableBindingOfFirstExpression();
- for (Prefix prefix: safePrefixes) {
- if (!prefix.getVariableBindingOfFirstExpression().isEqualTo(binding))
- return true;
- }
- return false;
+ return hasMoreThanOnePossibleTarget;
}
public boolean hasOnlyOnePossibleTarget() {
}
public int getTargetFrequency() {
- if (hasMoreThanOnePossibleTarget())
- ; // TODO: throw exception?
- return analyzer.calculateMostFrequentPrefix().getCount();
+ return targetFrequency;
}
public boolean hasNoUnfixes() {
- return analyzer.getUnfixes().isEmpty();
+ return hasNoUnfixes;
}
public boolean hasUnfixes() {
return !hasNoUnfixes();
}
- public IBinding calculateOriginalTarget() {
- return analyzer.calculateOriginalTarget();
+ public IVariableBinding calculateOriginalTarget() {
+ return restoreOriginalTarget();
+ }
+
+ private IVariableBinding restoreOriginalTarget() {
+ VariableBindingFinder variableBindingFinder = new VariableBindingFinder(originalTargetKey);
+ textSelection.getCoveringNode().accept(variableBindingFinder);
+ assertThat(variableBindingFinder.getVariableBinding(), notNullValue());
+ return variableBindingFinder.getVariableBinding();
}
@Override
--- /dev/null
+package no.uio.ifi.refaktor.analyze;
+
+import org.eclipse.jdt.core.dom.ASTNode;
+import org.eclipse.jdt.core.dom.ASTVisitor;
+import org.eclipse.jdt.core.dom.IBinding;
+import org.eclipse.jdt.core.dom.IVariableBinding;
+import org.eclipse.jdt.core.dom.SimpleName;
+
+public class VariableBindingFinder extends ASTVisitor {
+ private String bindingKey;
+ private boolean bindingFound;
+ private IVariableBinding variableBinding;
+
+ public VariableBindingFinder(String bindingKey) {
+ this.bindingKey = bindingKey;
+ bindingFound = false;
+ }
+
+ @Override
+ public boolean visit(SimpleName node) {
+ IBinding binding = node.resolveBinding();
+
+ if (binding instanceof IVariableBinding && binding.getKey().equals(bindingKey)) {
+ variableBinding = (IVariableBinding) binding;
+ bindingFound = true;
+ }
+
+ return false;
+ }
+
+ @Override
+ public boolean preVisit2(ASTNode node) {
+ return !bindingFound;
+ }
+
+ public IVariableBinding getVariableBinding() {
+ return variableBinding;
+ }
+}
*/
public class CompilationUnitTextSelection extends TextSelection implements ITextSelection {
+ private class NodeFinderCache {
+ private NodeFinder nodeFinder;
+
+ private NodeFinder getNodeFinder() {
+ if (nodeFinder == null)
+ nodeFinder = ParseUtils.createNodeFinder(ParseUtils.parse(compilationUnit), CompilationUnitTextSelection.this);
+ return nodeFinder;
+ }
+
+ public void dropCachedData() {
+ nodeFinder = null;
+ }
+ }
+
private ICompilationUnit compilationUnit;
- private NodeFinder nodeFinder;
+ private final NodeFinderCache nodeFinderCache;
public CompilationUnitTextSelection(ICompilationUnit compilationUnit, int offset, int length) {
super(offset, length);
if (compilationUnit == null)
throw new NullPointerException(this.getClass().getCanonicalName() + ": given compilation unit cannot be null");
this.compilationUnit = compilationUnit;
+ nodeFinderCache = new NodeFinderCache();
}
public CompilationUnitTextSelection(ICompilationUnit compilationUnit, ITextSelection selection) {
}
private NodeFinder getNodeFinder() {
- if (nodeFinder == null)
- nodeFinder = ParseUtils.createNodeFinder(ParseUtils.parse(compilationUnit), this);
- return nodeFinder;
+ return nodeFinderCache.getNodeFinder();
}
public boolean surroundsNode(ASTNode node) {
return super.equals(obj) && compilationUnit.equals(((CompilationUnitTextSelection)obj).compilationUnit);
return false;
}
-
+
@Override
public int hashCode() {
return (getOffset() << 24) | (getLength() << 16) | compilationUnit.hashCode();
}
-
+
@Override
public String toString() {
return "Offset: " + getOffset() + "; Length: " + getLength() + "; End: " + getEnd() + "; CU handle identifier: " + compilationUnit.getHandleIdentifier();
}
-
+
@Override
public int getStartLine() {
return createTextSelectionWithDocument().getStartLine();
}
-
+
@Override
public int getEndLine() {
return createTextSelectionWithDocument().getEndLine();
}
-
+
@Override
public String getText() {
return createTextSelectionWithDocument().getText();
}
-
+
private TextSelection createTextSelectionWithDocument() {
return new TextSelection(getDocument(), getOffset(), getLength());
}
+
+ public void dropCachedData() {
+ nodeFinderCache.dropCachedData();
+ }
}