Fixed index variable case

This commit is contained in:
Valentin Kipyatkov
2016-10-17 18:08:38 +03:00
parent e5fcfae969
commit 5c8db294df
4 changed files with 39 additions and 10 deletions
@@ -118,31 +118,39 @@ abstract class FilterTransformationBase : SequenceTransformation {
conditions: List<AtomicCondition>, conditions: List<AtomicCondition>,
restStatements: List<KtExpression> restStatements: List<KtExpression>
): List<FilterTransformationBase> { ): List<FilterTransformationBase> {
//TODO: indexVariable case
if (conditions.size == 1) { if (conditions.size == 1) {
return createFilterTransformation(loop, inputVariable, indexVariable, conditions.single()).singletonList() return createFilterTransformation(loop, inputVariable, indexVariable, conditions.single()).singletonList()
} }
val transformations = ArrayList<FilterTransformationBase>() var transformations = conditions.map { createFilterTransformation(loop, inputVariable, indexVariable, it) }
for (condition in conditions) {
val transformation = createFilterTransformation(loop, inputVariable, indexVariable, condition) val resultTransformations = ArrayList<FilterTransformationBase>()
val lastUseOfIndex = transformations.lastOrNull { it.indexVariable != null }
if (lastUseOfIndex != null) {
val index = transformations.indexOf(lastUseOfIndex)
val condition = CompositeCondition.create(conditions.take(index + 1))
resultTransformations.add(createFilterTransformation(loop, inputVariable, indexVariable, condition))
transformations = transformations.drop(index + 1)
}
for ((transformation, condition) in transformations.zip(conditions)) {
if (transformation !is FilterTransformation && isSmartCastUsed(inputVariable, restStatements)) { // filterIsInstance of filterNotNull if (transformation !is FilterTransformation && isSmartCastUsed(inputVariable, restStatements)) { // filterIsInstance of filterNotNull
transformations.add(transformation) resultTransformations.add(transformation)
} }
else { else {
val prevFilter = transformations.lastOrNull() as? FilterTransformation val prevFilter = resultTransformations.lastOrNull() as? FilterTransformation
if (prevFilter != null) { if (prevFilter != null) {
val mergedCondition = CompositeCondition.create(prevFilter.effectiveCondition.toAtomicConditions() + transformation.effectiveCondition.toAtomicConditions()) val mergedCondition = CompositeCondition.create(prevFilter.effectiveCondition.toAtomicConditions() + transformation.effectiveCondition.toAtomicConditions())
val mergedTransformation = createFilterTransformation(loop, inputVariable, indexVariable, mergedCondition, onlyFilterOrFilterNot = true) val mergedTransformation = createFilterTransformation(loop, inputVariable, indexVariable, mergedCondition, onlyFilterOrFilterNot = true)
transformations[transformations.lastIndex] = mergedTransformation resultTransformations[resultTransformations.lastIndex] = mergedTransformation
} }
else { else {
transformations.add(createFilterTransformation(loop, inputVariable, indexVariable, condition, onlyFilterOrFilterNot = true)) resultTransformations.add(createFilterTransformation(loop, inputVariable, indexVariable, condition, onlyFilterOrFilterNot = true))
} }
} }
} }
return transformations return resultTransformations
} }
private fun matchOneTransformation(state: MatchingState): Pair<SequenceTransformation, MatchingState>? { private fun matchOneTransformation(state: MatchingState): Pair<SequenceTransformation, MatchingState>? {
@@ -0,0 +1,9 @@
// WITH_RUNTIME
// IS_APPLICABLE: false
// IS_APPLICABLE_2: false
fun foo(list: List<Any>, out: MutableList<String>){
<caret>for ((i, any) in list.withIndex()) {
if (any is String && i % 2 == 0)
out.add(any)
}
}
@@ -370,6 +370,12 @@ public class IntentionTest2Generated extends AbstractIntentionTest2 {
doTest(fileName); doTest(fileName);
} }
@TestMetadata("cannotSplitOutFilterIsInstance.kt")
public void testCannotSplitOutFilterIsInstance() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/testData/intentions/loopToCallChain/filter/cannotSplitOutFilterIsInstance.kt");
doTest(fileName);
}
@TestMetadata("doNotSplitOutFilterIsInstance.kt") @TestMetadata("doNotSplitOutFilterIsInstance.kt")
public void testDoNotSplitOutFilterIsInstance() throws Exception { public void testDoNotSplitOutFilterIsInstance() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/testData/intentions/loopToCallChain/filter/doNotSplitOutFilterIsInstance.kt"); String fileName = KotlinTestUtils.navigationMetadata("idea/testData/intentions/loopToCallChain/filter/doNotSplitOutFilterIsInstance.kt");
@@ -8278,6 +8278,12 @@ public class IntentionTestGenerated extends AbstractIntentionTest {
doTest(fileName); doTest(fileName);
} }
@TestMetadata("cannotSplitOutFilterIsInstance.kt")
public void testCannotSplitOutFilterIsInstance() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/testData/intentions/loopToCallChain/filter/cannotSplitOutFilterIsInstance.kt");
doTest(fileName);
}
@TestMetadata("doNotSplitOutFilterIsInstance.kt") @TestMetadata("doNotSplitOutFilterIsInstance.kt")
public void testDoNotSplitOutFilterIsInstance() throws Exception { public void testDoNotSplitOutFilterIsInstance() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/testData/intentions/loopToCallChain/filter/doNotSplitOutFilterIsInstance.kt"); String fileName = KotlinTestUtils.navigationMetadata("idea/testData/intentions/loopToCallChain/filter/doNotSplitOutFilterIsInstance.kt");