336. palindrome of
To set a unique set of words, to find all the different index pair (i, j), so that the two words in the list, words [i] + words [j], can be spliced into a palindromic sequence.
Example 1:
Input: [ "abcd", "dcba ", "lls", "s", "sssll"]
Output: [[0,1], [1,0], [3,2], [2,4]]
explanation: may be spliced into the palindromic sequence is [ "dcbaabcd", "abcddcba" , "slls", "llssssll"]
example 2:
Input: [ "bat", "tab ", "cat"]
Output: [[0,1], [1,0]]
Explanation: may be spliced into the palindromic sequence is [ "battab", "tabbat" ]
PS:
string reverse trie constructed, and then determines whether the current string is present in the dictionary tree, such as the presence of other strings prove the existence of sub-strings and the string is equal to the mirror, the average length of the substring is defined k, the complexity of O (N * K ^ 2)
class Solution {
private static List<List<Integer>> ans = new ArrayList<>();
public List<List<Integer>> palindromePairs(String[] words) {
if (words == null || words.length == 0) {
return null;
}
ans = new ArrayList<>();
TrieNode root = new TrieNode();
for (int i = 0; i < words.length; i++) {
addWord(root, words[i], i);
}
for (int i = 0; i < words.length; i++) {
find(root, words[i], i);
}
return ans;
}
private static class TrieNode {
//当前字符串的数组位置,下游节点,以及能构成当前串or回文子串节点的数组位置集合
int index;
TrieNode[] next;
List<Integer> palindIndex;
public TrieNode() {
index = -1;
next = new TrieNode[26];
palindIndex = new ArrayList<>();
}
}
private static void addWord(TrieNode root, String word, int index) {
for (int i = word.length() - 1; i >= 0; i--) {
int ch = word.charAt(i) - 'a';
if (root.next[ch] == null) {
root.next[ch] = new TrieNode();
}
if (isPalindrome(word, 0, i)) {
root.palindIndex.add(index);
}
root = root.next[ch];
}
root.index = index;
root.palindIndex.add(index);
}
private static void find(TrieNode root, String word, int index) {
for (int i = 0; i < word.length(); i++) {
//待匹配串比字典树子串长,如asadcc匹配树上的asad
if (root.index != -1 && root.index != index && isPalindrome(word, i, word.length() - 1)) {
ans.add(Arrays.asList(index, root.index));
}
//System.out.println("root index:" + root.index);
if (root.next[word.charAt(i) - 'a'] == null) {
return;
}
root = root.next[word.charAt(i) - 'a'];
}
//待匹配串比字典树子串短,如asad匹配树上的asadcc
for (int i : root.palindIndex) {
if (i != index) {
ans.add(Arrays.asList(index, i));
}
}
}
private static boolean isPalindrome(String string, int l, int r) {
while (l < r) {
if (string.charAt(l++) != string.charAt(r--)) {
return false;
}
}
return true;
}
}