Last active
March 10, 2019 12:23
-
-
Save ezhov-da/6a919ff6dc49676a753ebe823fffaedf to your computer and use it in GitHub Desktop.
java cross join list
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<p>Бывает так, что необходимо сделать cross join данных из List<T>, основываясь на подсказке со <a href="http://stackoverflow.com/questions/38568550/cross-join-two-lists-java">stackoverflow</a>, специально для такого случая я написал пару классов:</p> | |
[code:]LANG[:code]import java.lang.reflect.Array; | |
import java.util.List; | |
import java.util.Objects; | |
import java.util.logging.Logger; | |
import java.util.stream.Collectors; | |
/** | |
* Делаем cross join списков | |
* <p> | |
* @author ezhov_da | |
*/ | |
public class CrossJoinList<T> | |
{ | |
private static final Logger LOG = Logger.getLogger(CrossJoinList.class.getName()); | |
private static CrossJoinList listCrossJoin; | |
public static CrossJoinList getInstance() | |
{ | |
if (Objects.isNull(listCrossJoin)) | |
{ | |
listCrossJoin = new CrossJoinList(); | |
} | |
return listCrossJoin; | |
} | |
public List<ObjectCrossJoin<T>> crossJoinTwoList(Class<T> clazz, List<T> listOne, List<T> listTwo) | |
{ | |
return listOne | |
.stream() | |
.flatMap(t | |
-> listTwo | |
.stream() | |
.map(t1 -> | |
{ | |
T[] array = (T[]) Array.newInstance(clazz, 2); | |
array[0] = t; | |
array[1] = t1; | |
return new ObjectCrossJoin<T>(array); | |
} | |
) | |
).collect(Collectors.toList()); | |
} | |
List<ObjectCrossJoin<T>> objectCrossJoins; | |
public synchronized List<ObjectCrossJoin<T>> executeCrossJoin(Class<T> clazz, List<T>... listsForJoin) | |
{ | |
switch (listsForJoin.length) | |
{ | |
case 0: | |
case 1: | |
throw new IllegalArgumentException("Not use for join one list. Min two list."); | |
case 2: | |
return crossJoinTwoList(clazz, listsForJoin[0], listsForJoin[1]); | |
default: | |
//сделано для того, чтоб cross join проводился в последовательности следования массива | |
List<T> listOne = listsForJoin[listsForJoin.length - 2]; | |
List<T> listTwo = listsForJoin[listsForJoin.length - 1]; | |
objectCrossJoins = crossJoinTwoList(clazz, listOne, listTwo); | |
for (int i = listsForJoin.length - 3; i >= 0; i--) | |
{ | |
objectCrossJoins = listsForJoin[i] | |
.stream() | |
.flatMap(t | |
-> objectCrossJoins | |
.stream() | |
.map((ObjectCrossJoin<T> t1) -> | |
{ | |
T[] array = t1.getArrayCrossJoin(); | |
final T[] arrayResult = (T[]) Array.newInstance(clazz, array.length + 1); | |
arrayResult[0] = t; | |
for (int i1 = 1; i1 < arrayResult.length; i1++) | |
{ | |
arrayResult[i1] = array[i1 - 1]; | |
} | |
ObjectCrossJoin<T> objectCrossJoin = new ObjectCrossJoin<>(arrayResult); | |
return objectCrossJoin; | |
}) | |
).collect(Collectors.toList()); | |
} | |
return objectCrossJoins; | |
} | |
} | |
} | |
import java.util.logging.Logger; | |
import java.util.stream.Collectors; | |
import java.util.stream.Stream; | |
/** | |
* Объект для замножения | |
* <p> | |
* @author ezhov_da | |
*/ | |
public class ObjectCrossJoin<T> | |
{ | |
private static final Logger LOG = Logger.getLogger(ObjectCrossJoin.class.getName()); | |
private T[] arrayCrossJoin; | |
public ObjectCrossJoin(T... arrayCrossJoin) | |
{ | |
this.arrayCrossJoin = arrayCrossJoin; | |
} | |
public T[] getArrayCrossJoin() | |
{ | |
return arrayCrossJoin; | |
} | |
@Override | |
public String toString() | |
{ | |
return Stream.of(arrayCrossJoin).map(t -> t.toString()).collect(Collectors.joining(",")); | |
} | |
} | |
[/code] |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment