Reputation: 35
I think this may be a very simple solution but I am not too sure.
I am trying to create an array of characters, sort through them by incrementing a particular index of the array and throwing them into a string at the end.
I have accomplished this, (verified via printing the result out to the console. "aaaaaaaa" to "aaaaaaab" and so on. However, my new version of the code sorts through ASCII Values 33 - 126. '!' to '~'
Now, the one thing I am trying to do is call that string in the main method so that the encryption/decryption program that we were assigned, can use this string over and over again.
The program we were originally assigned can be found here: http://www.avajava.com/tutorials/lessons/how-do-i-encrypt-and-decrypt-files-using-des.html
import java.lang.Class.*;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import javax.crypto.Cipher;
import javax.crypto.CipherInputStream;
import javax.crypto.CipherOutputStream;
import javax.crypto.SecretKey;
import javax.crypto.SecretKeyFactory;
import javax.crypto.spec.DESKeySpec;
public class Example1 {
public String keyGen() {
//create an array used for storing each character
char array[] = new char[8];
//for loop checks for each character between '!' and '~'
for (char c0 = '!'; c0 <= '~'; c0++) {
array[0] = c0;
for (char c1 = '!'; c1 <= '~'; c1++) {
array[1] = c1;
for (char c2 = '!'; c2 <= '~'; c2++) {
array[2] = c2;
for (char c3 = '!'; c3 <= '~'; c3++) {
array[3] = c3;
for (char c4 = '!'; c4 <= '~'; c4++) {
array[4] = c4;
for (char c5 = '!'; c5 <= '~'; c5++) {
array[5] = c5;
for (char c6 = '!'; c6 <= '~'; c6++) {
array[6] = c6;
for (char c7 = '!'; c7 <= '~'; c7++) {
array[7] = c7;
//create new string that stores the array
String pKey = new String(array);
//trying to return the new string
return pKey;
}
}
}
}
}
}
}
}
}
public static void main(String []args) {
try {
// I am getting an error here; I know it has something to do with static references
String key = new String(keyGen(pKey);
// needs to be at least 8 characters for DES
FileInputStream fis = new FileInputStream("original.txt");
FileOutputStream fos = new FileOutputStream("encrypted.txt");
encrypt(key, fis, fos);
FileInputStream fis2 = new FileInputStream("encrypted.txt");
FileOutputStream fos2 = new FileOutputStream("decrypted.txt");
decrypt(key, fis2, fos2);
} catch (Throwable e) {
e.printStackTrace();
}
}
public static void encrypt(String key, InputStream is, OutputStream os) throws Throwable {
encryptOrDecrypt(key, Cipher.ENCRYPT_MODE, is, os);
}
public static void decrypt(String key, InputStream is, OutputStream os) throws Throwable {
encryptOrDecrypt(key, Cipher.DECRYPT_MODE, is, os);
}
public static void encryptOrDecrypt(String key, int mode, InputStream is, OutputStream os) throws Throwable {
DESKeySpec dks = new DESKeySpec(key.getBytes());
SecretKeyFactory skf = SecretKeyFactory.getInstance("DES");
SecretKey desKey = skf.generateSecret(dks);
Cipher cipher = Cipher.getInstance("DES"); // DES/ECB/PKCS5Padding for SunJCE
if (mode == Cipher.ENCRYPT_MODE) {
cipher.init(Cipher.ENCRYPT_MODE, desKey);
CipherInputStream cis = new CipherInputStream(is, cipher);
doCopy(cis, os);
} else if (mode == Cipher.DECRYPT_MODE) {
cipher.init(Cipher.DECRYPT_MODE, desKey);
CipherOutputStream cos = new CipherOutputStream(os, cipher);
doCopy(is, cos);
}
}
public static void doCopy(InputStream is, OutputStream os) throws IOException {
byte[] bytes = new byte[64];
int numBytes;
while ((numBytes = is.read(bytes)) != -1) {
os.write(bytes, 0, numBytes);
}
os.flush();
os.close();
is.close();
}
}
Thi
Upvotes: 2
Views: 1293
Reputation: 37813
Hope this helps you solve the problem. As for right now, your keyGen()
is equivalent to the following code:
public String keyGen() {
return "!!!!!!!!";
}
because you return the value as soon as you enter the innermost for
loop. Maybe you want to change the method to return a List<String>
and add your strings in the innermost for
loop to that list, and return that list after all of the for
loops? This way you could iterate through the list in your main
method.
If I have counted correct, there are 93^8 = 5.595.818.096.650.401 different strings. It was bad advice to store all those in a list. Dukeling noted in the comments, that it would be better to use a custom Iterator<String>
for that.
EDIT
Here's an implementation of such an iterator:
import java.util.Arrays;
import java.util.Iterator;
public class BruteForceIterator implements Iterator<String> {
private char min, max;
private char[] current;
private char[] last;
private int reachedLast = 0;
public BruteForceIterator(char min, char max, int length) {
this.min = min;
this.max = max;
current = new char[length];
Arrays.fill(current, min);
last = new char[length];
Arrays.fill(last, max);
}
@Override
public boolean hasNext() {
return reachedLast < 2;
}
@Override
public String next() {
String str = new String(current);
for(int i = current.length - 1; i >= 0; i--) {
char next = following(current[i]);
current[i] = next;
if (next != min) {
break;
}
}
if (Arrays.equals(current, last) || reachedLast > 0) {
reachedLast++;
}
return str;
}
private char following(char in) {
if (in < max) {
return (char) (in + 1);
} else {
return min;
}
}
@Override
public void remove() {
throw new UnsupportedOperationException("No with me, sir!");
}
public static void main(String[] args) {
BruteForceIterator bit = new BruteForceIterator('a', 'c', 3);
while (bit.hasNext()) {
System.out.println(bit.next());
}
}
}
Upvotes: 3