Created
February 1, 2018 18:17
-
-
Save EvanOman/767b482f073845ba2856923cbcaa0788 to your computer and use it in GitHub Desktop.
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
package testing; | |
import java.math.BigInteger; | |
import java.util.List; | |
import java.util.stream.Collectors; | |
import java.util.stream.Stream; | |
public class IsAnagramDemo | |
{ | |
/* Get the primes we need */ | |
private static final List<BigInteger> alphaPrimes = primes() | |
.limit(26) | |
.collect(Collectors.toList()); | |
/* Int encoding of lowercase a in unicode */ | |
private static final int A_INT_ENCODING = 97; | |
/* Int encoding of lowercase z in unicode */ | |
private static final int Z_INT_ENCODING = 122; | |
/* | |
Main method to demonstrate success | |
*/ | |
public static void main(String[] args) throws Exception | |
{ | |
assert isAnagram("stressed", "desserts"); | |
assert !isAnagram("happy", "sad"); | |
} | |
/** | |
* Determines if two strings are anagrams using the prime product method | |
* | |
* @param s1 First input string | |
* @param s2 Second input string | |
* @return Boolean indicating anagram-ness | |
* @throws IllegalArgumentException Thrown when at least one of the input strings is invalid | |
*/ | |
public static boolean isAnagram(String s1, String s2) throws IllegalArgumentException | |
{ | |
return primeProduct(s1).equals(primeProduct(s2)); | |
} | |
/** | |
* Converts a string to the corresponding product of prime values | |
* | |
* @param s Input string | |
* @return Big integer product of primes | |
* @throws IllegalArgumentException Thrown when strong contains chars outside of A-z | |
*/ | |
private static BigInteger primeProduct(String s) throws IllegalArgumentException | |
{ | |
/* Convert to lowercase char array */ | |
char[] chars = s.toLowerCase().toCharArray(); | |
BigInteger product = BigInteger.ONE; | |
for (char c : chars) | |
{ | |
/* Cast char to int */ | |
int cInt = (int)c; | |
/* If the char is out of bounds we must throw an exception */ | |
if (cInt < A_INT_ENCODING || cInt > Z_INT_ENCODING) | |
{ | |
throw new IllegalArgumentException("Character \"" + c + "\" not valid"); | |
} | |
/* Otherwise we can do the prime lookup */ | |
else | |
{ | |
/* Prime value corresponding to this char */ | |
BigInteger primeVal = alphaPrimes.get(cInt % A_INT_ENCODING); | |
/* Add this prime to our product */ | |
product = product.multiply(primeVal); | |
} | |
} | |
/* Return the product */ | |
return product; | |
} | |
/** | |
* @return Infinite stream of primes | |
*/ | |
private static Stream<BigInteger> primes() | |
{ | |
return Stream.iterate(BigInteger.valueOf(2L), n -> n.add(BigInteger | |
.ONE)).filter(n -> n.isProbablePrime(10)); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment