-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
add unify method to Birthmarks class
- Loading branch information
Showing
7 changed files
with
149 additions
and
1 deletion.
There are no files selected for viewing
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
61 changes: 61 additions & 0 deletions
61
pochi-api/src/main/java/jp/cafebabe/birthmarks/entities/BirthmarksMerger.java
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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,61 @@ | ||
package jp.cafebabe.birthmarks.entities; | ||
|
||
import io.vavr.control.Try; | ||
import jp.cafebabe.birthmarks.utils.LongestCommonSubstring; | ||
import jp.cafebabe.kunai.entries.ClassName; | ||
|
||
import java.net.URI; | ||
import java.nio.file.Path; | ||
import java.util.Optional; | ||
import java.util.stream.Collectors; | ||
import java.util.stream.Stream; | ||
|
||
class BirthmarksMerger { | ||
public <T> Optional<Birthmark<T>> unify(Birthmarks<T> birthmarks) { | ||
Optional<Elements<T>> elements = mergeElements(birthmarks); | ||
Metadata metadata = mergeMetadata(birthmarks); | ||
return elements.map(e -> new Birthmark<>(metadata, e)); | ||
} | ||
|
||
private <T> Metadata mergeMetadata(Birthmarks<T> birthmarks) { | ||
String location = findCommonLocation(birthmarks.stream()); | ||
return constructMetadata(location, findType(birthmarks)); | ||
} | ||
|
||
private <T> Optional<BirthmarkType> findType(Birthmarks<T> birthmarks) { | ||
return birthmarks.stream().map(b -> b.type()) | ||
.collect(Collectors.reducing((a, b) -> a)); | ||
} | ||
|
||
private Metadata constructMetadata(String location, Optional<BirthmarkType> type) { | ||
Try<URI> tryUri = Try.of(() -> new URI(location)); | ||
Optional<URI> uri = tryUri.toJavaOptional(); | ||
Optional<ClassName> name = uri.map(u -> new ClassName(findBaseName(u))); | ||
return new Metadata(name.orElseGet(() -> new ClassName("<merged>")), uri.get(), type.get()); | ||
} | ||
|
||
private String findBaseName(URI uri) { | ||
String path = uri.toString(); | ||
int index = path.lastIndexOf('/'); | ||
if(index >= 0) | ||
return path.substring(index + 1); | ||
return path; | ||
} | ||
|
||
private <T> String findCommonLocation(Stream<Birthmark<T>> stream) { | ||
Optional<String> location = stream.map(birthmark -> birthmark.metadata()) | ||
.map(m -> m.location().toString()) | ||
.collect(Collectors.reducing((s1, s2) -> LongestCommonSubstring.of(s1, s2))); | ||
return location.orElseGet(() -> ""); | ||
} | ||
|
||
private <T> Optional<Elements<T>> mergeElements(Birthmarks<T> birthmarks) { | ||
return birthmarks.stream() | ||
.map(birthmark -> birthmark.elements()) | ||
.collect(Collectors.reducing((a, b) -> a.merge(b))); | ||
} | ||
|
||
public static <T> Optional<Birthmark<T>> unifyTo(Birthmarks<T> birthmarks) { | ||
return new BirthmarksMerger().unify(birthmarks); | ||
} | ||
} |
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
47 changes: 47 additions & 0 deletions
47
pochi-api/src/main/java/jp/cafebabe/birthmarks/utils/LongestCommonSubstring.java
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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
package jp.cafebabe.birthmarks.utils; | ||
|
||
import jp.cafebabe.birthmarks.entities.Couple; | ||
|
||
import java.util.Optional; | ||
|
||
public class LongestCommonSubstring { | ||
public static final String of(String s1, String s2) { | ||
return new LongestCommonSubstring() | ||
.calculate(s1, s2); | ||
} | ||
|
||
private String calculate(String s1, String s2) { | ||
int[][] table = new int[s1.length() + 1][s2.length() + 1]; | ||
Result r = Result.of(0, 0, 0); | ||
for(int i = 0; i < table.length; i++) { | ||
for(int j = 0; j < table[i].length; j++) { | ||
if(i == 0 || j == 0) table[i][j] = 0; | ||
else if(s1.charAt(i - 1) == s2.charAt(j - 1)) { | ||
table[i][j] = 1 + table[i - 1][j - 1]; | ||
r = updateResultIfNeeded(r, i, j, table[i][j]); | ||
} | ||
// printTable(table); | ||
} | ||
} | ||
return s1.substring(r.i - r.max, r.i); | ||
} | ||
|
||
private Result updateResultIfNeeded(Result r, int i, int j, int v) { | ||
if(r.max > v) | ||
return r; | ||
return Result.of(i, j, v); | ||
} | ||
|
||
private static final class Result { | ||
private int i, j; | ||
private int max; | ||
private Result(int i, int j, int max) { | ||
this.i = i; | ||
this.j = j; | ||
this.max = max; | ||
} | ||
public static Result of(int i, int j, int max) { | ||
return new Result(i, j, max); | ||
} | ||
} | ||
} |
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
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
15 changes: 15 additions & 0 deletions
15
pochi-api/src/test/java/jp/cafebabe/birthmarks/utils/LongestCommonSubstringTest.java
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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
package jp.cafebabe.birthmarks.utils; | ||
|
||
import static org.hamcrest.MatcherAssert.assertThat; | ||
import static org.hamcrest.Matchers.is; | ||
|
||
import org.junit.Test; | ||
|
||
public class LongestCommonSubstringTest { | ||
@Test | ||
public void basicTest() { | ||
assertThat(LongestCommonSubstring.of("abcdxyz", "xyzabcd"), is("abcd")); | ||
assertThat(LongestCommonSubstring.of("abracadabra", "open sesame"), is("a")); | ||
assertThat(LongestCommonSubstring.of("aaaa", "bbb"), is("")); | ||
} | ||
} |