1010import java .util .Map ;
1111
1212public class Solution {
13- public List <List <Integer >> supersequences (String [] wordsArray ) {
14- List <String > words = new ArrayList <>(Arrays .asList (wordsArray ));
15- Collections .sort (words );
16- int [] bg = new int [26 ];
17- Arrays .fill (bg , -1 );
18- int [] ed = new int [26 ];
19- Arrays .fill (ed , 0 );
13+ private Map <String , Boolean > buildWordMap (List <String > words ) {
2014 Map <String , Boolean > mp = new HashMap <>();
21- Map <Character , Boolean > mp2 = new HashMap <>();
2215 for (String x : words ) {
2316 mp .put (x , true );
17+ }
18+ return mp ;
19+ }
20+
21+ private Map <Character , Boolean > buildCharMap (List <String > words ) {
22+ Map <Character , Boolean > mp2 = new HashMap <>();
23+ for (String x : words ) {
2424 mp2 .put (x .charAt (0 ), true );
2525 mp2 .put (x .charAt (1 ), true );
2626 }
27+ return mp2 ;
28+ }
29+
30+ private int [] initializeAnswerArray (Map <String , Boolean > mp , Map <Character , Boolean > mp2 ) {
2731 int [] tans = new int [26 ];
2832 Arrays .fill (tans , 0 );
2933 for (char c = 'a' ; c <= 'z' ; c ++) {
@@ -34,19 +38,102 @@ public List<List<Integer>> supersequences(String[] wordsArray) {
3438 tans [c - 'a' ] = 1 ;
3539 }
3640 }
41+ return tans ;
42+ }
43+
44+ private List <String > filterWords (List <String > words , int [] tans ) {
3745 List <String > wtc = new ArrayList <>();
3846 for (String x : words ) {
3947 if (tans [x .charAt (0 ) - 'a' ] != 2 && tans [x .charAt (1 ) - 'a' ] != 2 ) {
4048 wtc .add (x );
4149 }
4250 }
51+ return wtc ;
52+ }
53+
54+ private void updateBoundaries (List <String > wtc , int [] bg , int [] ed ) {
4355 for (int i = 0 ; i < wtc .size (); i ++) {
4456 int l = wtc .get (i ).charAt (0 ) - 'a' ;
4557 if (bg [l ] == -1 ) {
4658 bg [l ] = i ;
4759 }
4860 ed [l ] = i ;
4961 }
62+ }
63+
64+ private List <Integer > findMinimalSolutions (List <String > wtc , int [] tans , int [] bg , int [] ed ) {
65+ List <Integer > ns = new ArrayList <>();
66+ for (int i = 0 ; i < 26 ; i ++) {
67+ if (tans [i ] == 1 ) {
68+ ns .add (i );
69+ }
70+ }
71+ List <Integer > gm = new ArrayList <>();
72+ for (int i = 0 ; i < (1 << ns .size ()); i ++) {
73+ if (isValidSolution (i , ns , wtc , tans .clone (), bg , ed )) {
74+ gm .add (i );
75+ }
76+ }
77+ return gm ;
78+ }
79+
80+ private boolean isValidSolution (
81+ int i , List <Integer > ns , List <String > wtc , int [] tans , int [] bg , int [] ed ) {
82+ int [] indg = new int [26 ];
83+ Arrays .fill (indg , 0 );
84+ for (int j = 0 ; j < ns .size (); j ++) {
85+ if ((i & (1 << j )) != 0 ) {
86+ tans [ns .get (j )] = 2 ;
87+ } else {
88+ tans [ns .get (j )] = 1 ;
89+ }
90+ }
91+ for (String w : wtc ) {
92+ if (tans [w .charAt (0 ) - 'a' ] != 2 && tans [w .charAt (1 ) - 'a' ] != 2 ) {
93+ indg [w .charAt (1 ) - 'a' ]++;
94+ }
95+ }
96+ return processIndegrees (indg , tans , wtc , bg , ed );
97+ }
98+
99+ private boolean processIndegrees (int [] indg , int [] tans , List <String > wtc , int [] bg , int [] ed ) {
100+ List <Integer > chk = new ArrayList <>();
101+ for (int j = 0 ; j < 26 ; j ++) {
102+ if (indg [j ] == 0 && tans [j ] == 1 ) {
103+ chk .add (j );
104+ }
105+ }
106+ while (!chk .isEmpty ()) {
107+ int u = chk .remove (chk .size () - 1 );
108+ if (bg [u ] == -1 ) {
109+ continue ;
110+ }
111+ for (int j = bg [u ]; j <= ed [u ]; j ++) {
112+ int l = wtc .get (j ).charAt (1 ) - 'a' ;
113+ if (tans [l ] == 2 ) {
114+ continue ;
115+ }
116+ indg [l ]--;
117+ if (indg [l ] == 0 ) {
118+ chk .add (l );
119+ }
120+ }
121+ }
122+ return Arrays .stream (indg ).max ().getAsInt () == 0 ;
123+ }
124+
125+ public List <List <Integer >> supersequences (String [] wordsArray ) {
126+ List <String > words = new ArrayList <>(Arrays .asList (wordsArray ));
127+ Collections .sort (words );
128+ int [] bg = new int [26 ];
129+ Arrays .fill (bg , -1 );
130+ int [] ed = new int [26 ];
131+ Arrays .fill (ed , 0 );
132+ Map <String , Boolean > mp = buildWordMap (words );
133+ Map <Character , Boolean > mp2 = buildCharMap (words );
134+ int [] tans = initializeAnswerArray (mp , mp2 );
135+ List <String > wtc = filterWords (words , tans );
136+ updateBoundaries (wtc , bg , ed );
50137 List <List <Integer >> ans = new ArrayList <>();
51138 if (wtc .isEmpty ()) {
52139 List <Integer > tansList = new ArrayList <>();
@@ -55,76 +142,33 @@ public List<List<Integer>> supersequences(String[] wordsArray) {
55142 }
56143 ans .add (tansList );
57144 return ans ;
58- } else {
59- List <Integer > ns = new ArrayList <>();
60- for (int i = 0 ; i < 26 ; i ++) {
61- if (tans [i ] == 1 ) {
62- ns .add (i );
63- }
145+ }
146+
147+ List <Integer > gm = findMinimalSolutions (wtc , tans , bg , ed );
148+ int minb = gm .stream ().mapToInt (Integer ::bitCount ).min ().getAsInt ();
149+
150+ List <Integer > ns = new ArrayList <>();
151+ for (int i = 0 ; i < 26 ; i ++) {
152+ if (tans [i ] == 1 ) {
153+ ns .add (i );
64154 }
65- List <Integer > gm = new ArrayList <>();
66- for (int i = 0 ; i < (1 << ns .size ()); i ++) {
67- int [] indg = new int [26 ];
68- Arrays .fill (indg , 0 );
155+ }
156+ for (int x : gm ) {
157+ if (Integer .bitCount (x ) == minb ) {
69158 for (int j = 0 ; j < ns .size (); j ++) {
70- if ((i & (1 << j )) != 0 ) {
159+ if ((x & (1 << j )) != 0 ) {
71160 tans [ns .get (j )] = 2 ;
72161 } else {
73162 tans [ns .get (j )] = 1 ;
74163 }
75164 }
76- for (String w : wtc ) {
77- if (tans [w .charAt (0 ) - 'a' ] != 2 && tans [w .charAt (1 ) - 'a' ] != 2 ) {
78- indg [w .charAt (1 ) - 'a' ]++;
79- }
80- }
81- List <Integer > chk = new ArrayList <>();
82- for (int j = 0 ; j < 26 ; j ++) {
83- if (indg [j ] == 0 && tans [j ] == 1 ) {
84- chk .add (j );
85- }
86- }
87- while (!chk .isEmpty ()) {
88- int u = chk .remove (chk .size () - 1 );
89- if (bg [u ] == -1 ) {
90- continue ;
91- }
92- for (int j = bg [u ]; j <= ed [u ]; j ++) {
93- int l = wtc .get (j ).charAt (1 ) - 'a' ;
94- if (tans [l ] == 2 ) {
95- continue ;
96- }
97- indg [l ]--;
98- if (indg [l ] == 0 ) {
99- chk .add (l );
100- }
101- }
102- }
103- if (Arrays .stream (indg ).max ().getAsInt () == 0 ) {
104- gm .add (i );
105- }
106- }
107- int minb = 20 ;
108- for (int x : gm ) {
109- minb = Math .min (minb , Integer .bitCount (x ));
110- }
111- for (int x : gm ) {
112- if (Integer .bitCount (x ) == minb ) {
113- for (int j = 0 ; j < ns .size (); j ++) {
114- if ((x & (1 << j )) != 0 ) {
115- tans [ns .get (j )] = 2 ;
116- } else {
117- tans [ns .get (j )] = 1 ;
118- }
119- }
120- List <Integer > tansList = new ArrayList <>();
121- for (int t : tans ) {
122- tansList .add (t );
123- }
124- ans .add (tansList );
165+ List <Integer > tansList = new ArrayList <>();
166+ for (int t : tans ) {
167+ tansList .add (t );
125168 }
169+ ans .add (tansList );
126170 }
127- return ans ;
128171 }
172+ return ans ;
129173 }
130174}
0 commit comments