Maximum input length exceeded of java program in linux shell - java

I've created a wonderfully working program that encrypts the text a person enters with a keyword of their choice. The program can decrypt the encrypted message/text by going in decrypt mode and entering the correct key.
Now my problem is that when I enter a text in the Linux shell that's longer than approximately 5000 characters, it doesn't process all the text. I used this German dummy text that's 15954 characters long. If I enter the text in the Linux shell It cuts off my text at about 4025 characters. On the other hand, if I execute the program in IntelliJ everything works like a charm. If you need the code I got on git here.
Thanks in advance. I appreciate the help.
My Start class that starts everything
public class Start
{
public static void main(String[] args)
{
Scanner scanner = new Scanner(System.in);
System.out.print("Would you like to encrypt or decrypt a message? [d/e]\n>");
char de = scanner.nextLine().charAt(0);
boolean _Encrypt = true;
if (de == 'd')
_Encrypt = false;
else if (de == 'e')
;
else
{
System.out.println("Non valid input. Please try again later.");
System.exit(1);
}
char[] text = ch.wagner.root.viginere.Input.getText("Text:\n>");
char[] key = ch.wagner.root.viginere.Input.getKey("Key:\n>");
if (_Encrypt)
{
System.out.println(ch.wagner.root.viginere.Process.encrypt(text, key));
}
else
{
System.out.println(ch.wagner.root.viginere.Process.decrypt(text, key));
}
}
}
My Input class
public class Input
{
public static char[] getText (String requestMessage)
{
boolean _AllowedToContinue = false;
char[] text = null;
while (!_AllowedToContinue)
{
System.out.print(requestMessage);
text = ch.wagner.root.viginere.Input.getCharArray();
if (!Input.inputValid(new String(text), "[^`^]+$"))
System.out.println("Invalid input. Try again.");
else
_AllowedToContinue = true;
}
// System.err.println(new String(text).length());
// Created this to check the length of the String after input
return text;
}
public static char[] getKey (String requestMessage)
{
boolean _AllowedToContinue = false;
char[] key = null;
while (!_AllowedToContinue)
{
System.out.print(requestMessage);
key = ch.wagner.root.viginere.Input.getCharArray();
if (!Input.inputValid(new String(key), "^[A-Za-z]+$"))
System.out.println("Invalid input. Try again.");
else
_AllowedToContinue = true;
}
return key;
}
private static boolean inputValid (String input, String regex)
{
boolean returnValue = true;
final Pattern pattern = Pattern.compile(regex);
if (!pattern.matcher(input).matches()) {
returnValue = false;
}
return returnValue;
}
private static String getString ()
{
Scanner scanner = new Scanner(System.in);
return scanner.nextLine();
}
private static char[] getCharArray ()
{
return getString().toCharArray();
}
}
The Process class that encrypts/decrypts the text
public class Process
{
public static String decrypt(char[] text, char[] key)
{
int[] shift = new int[key.length];
key = new String(key).toUpperCase().toCharArray();
for (int i = 0; i < shift.length; i++)
shift[i] = key[i] - 65;
int ii = 0;
for (int i = 0; i < text.length; i++)
{
if (ii == shift.length)
ii = 0;
if (Character.isLetter(text[i]))
{
if (((((text[i] - 65) - shift[ii]) % 26) + 65) < 65)
text[i] = (char) (((((text[i] - 65) - shift[ii]) % 26) + 65) + 26);
else
text[i] = (char) ((((text[i] - 65) - shift[ii]) % 26) + 65);
}
ii++;
}
return new String(text);
}
public static String encrypt(char[] text, char[] key)
{
int[] shift = new int[key.length];
key = new String(key).toUpperCase().toCharArray();
for (int i = 0; i < shift.length; i++)
{
shift[i] = key[i] - 65;
}
text = new String(text).replaceAll("[^a-zA-Z0-9|/()*]+", "").toCharArray();
int ii = 0;
for (int i = 0; i < text.length; i++)
{
if (ii == shift.length)
ii = 0;
text[i] = Character.toUpperCase(text[i]);
if (Character.isLetter(text[i]))
text[i] = (char)((((text[i] - 65) + shift[ii]) % 26) + 65);
ii++;
}
return new String(text);
}
}

Related

Caesar Cipher with Java Code - Will only read Uppercase

I'm just a beginning programmer, and I'm here to find a bug in my program. The program only reads the uppercase letters in my text file, even though I have a lowercase case in my encrypt and decrypt methods. I'm guessing it's a problem with the caesarEncipher method. (Ignore my Decipher case in the main, I will get to it soon.)
import java.util.*;
import java.io.*;
public class Cipher {
public static void main(String[] args) throws FileNotFoundException {
Scanner scan = new Scanner(System.in);
System.out.println("Welcome to CaesarCipher");
System.out.println();
System.out.println("Enter 1 to Encipher, 2 to Decipher, or -1 to exit");
int choice = 0;
do {
choice = scan.nextInt();
if (choice == 1) {
System.out.println("What non-negative shift should be used?");
int shift = scan.nextInt();
System.out.println("What is the input file name?");
String input = scan.next();
System.out.println("What is the output file name?");
String output = scan.next();
System.out.println(caesarEncipher(input, shift, output));
} else if (choice == 2) {
} else if (choice == -1) {
System.out.println("Thank you for using CaesarCipher");
break;
}
} while (choice != 1 && choice != 2 && choice != -1);
}
public static String caesarEncipher(String inputString, int shift, String output) throws FileNotFoundException {
File outFile = new File(output);
PrintStream encoded = new PrintStream(outFile); // creates new file for the output
File input = new File(inputString); // creates file with String to scan
Scanner scan = new Scanner(input); // creates Scanner
while (scan.hasNextLine()) {
String cipher = scan.nextLine(); // gets next line of file
String encipher = ""; // String to be added to new file
int i;
for (i = 0; i < cipher.length(); i++) {
String curr = cipher.substring(i, i + 1); // current character
String newChar = encrypt(curr, shift);
encipher = encipher + newChar;
}
encoded.println(encipher);
}
encoded.close();
return "DONE";
}
public static String encrypt(String str, int shift) {
String encrypted = "";
for (int i = 0; i < 1; i++) {
int c = str.charAt(i);
if (Character.isUpperCase(c)) {//if uppercase
c = c + (shift % 26);
if (c > 'Z') { //resets if it passes 'Z'
c = c - 26;
} else if (Character.isLowerCase(c)) {// if lowercase
c = c + (shift % 26);
if (c > 'z') { // resets if it passes 'z'
c = c - 26;
}
}
encrypted = encrypted + (char) c; // adds the encrypted character to the string
}
}
return encrypted;
}
public static String decrypt(String str, int shift) {
String decrypted = "";
for (int i = 0; i < 1; i++) {
int c = str.charAt(i);
if (Character.isUpperCase(c)) //if uppercase
{
c = c + (shift % 26);
if (c < 'A') { //resets if it passes 'A'
c = c + 26;
}
} else if (Character.isLowerCase(c)) // if lowercase
{
c = c + (shift % 26);
if (c < 'a') { // resets if it passes 'a'
c = c + 26;
}
}
decrypted = decrypted + (char) c; // adds the derypted character to the string
}
return decrypted;
}
}
In encrypt() method: This part of code
else if(Character.isLowerCase(c)) {
c=c+(shift%26);
if(c>'z') {
c=c-26;
}
}
encrypted=encrypted+(char)c;
belongs to if(c>'Z') instead of if(Character.isUpperCase(c))

Running 2 java codes

I have 2 java programs (ciphers), one is Playfair and second is Transposition.
Now i want to run Playfair code, then right after that compile Transposition using the result i got from Playfair code. How should i make this?(
Playfair code
import java.awt.Point;
import java.util.Scanner;
public class PlayfairCipher {
private static char[][] charTable;
private static Point[] positions;
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String key = prompt("Enter an encryption key (min length 6): ", sc, 6);
String txt = prompt("Enter the message: ", sc, 1);
String jti = prompt("Replace J with I? y/n: ", sc, 1);
boolean changeJtoI = jti.equalsIgnoreCase("y");
createTable(key, changeJtoI);
String enc = encode(prepareText(txt, changeJtoI));
System.out.printf("%nEncoded message: %n%s%n", enc);
System.out.printf("%nDecoded message: %n%s%n", decode(enc));
}
private static String prompt(String promptText, Scanner sc, int minLen) {
String s;
do {
System.out.print(promptText);
s = sc.nextLine().trim();
} while (s.length() < minLen);
return s;
}
private static String prepareText(String s, boolean changeJtoI) {
s = s.toUpperCase().replaceAll("[^A-Z]", "");
return changeJtoI ? s.replace("J", "I") : s.replace("Q", "");
}
private static void createTable(String key, boolean changeJtoI) {
charTable = new char[5][5];
positions = new Point[26];
String s = prepareText(key + "ABCDEFGHIJKLMNOPQRSTUVWXYZ", changeJtoI);
int len = s.length();
for (int i = 0, k = 0; i < len; i++) {
char c = s.charAt(i);
if (positions[c - 'A'] == null) {
charTable[k / 5][k % 5] = c;
positions[c - 'A'] = new Point(k % 5, k / 5);
k++;
}
}
}
private static String encode(String s) {
StringBuilder sb = new StringBuilder(s);
for (int i = 0; i < sb.length(); i += 2) {
if (i == sb.length() - 1)
sb.append(sb.length() % 2 == 1 ? 'X' : "");
else if (sb.charAt(i) == sb.charAt(i + 1))
sb.insert(i + 1, 'X');
}
return codec(sb, 1);
}
private static String decode(String s) {
return codec(new StringBuilder(s), 4);
}
private static String codec(StringBuilder text, int direction) {
int len = text.length();
for (int i = 0; i < len; i += 2) {
char a = text.charAt(i);
char b = text.charAt(i + 1);
int row1 = positions[a - 'A'].y;
int row2 = positions[b - 'A'].y;
int col1 = positions[a - 'A'].x;
int col2 = positions[b - 'A'].x;
if (row1 == row2) {
col1 = (col1 + direction) % 5;
col2 = (col2 + direction) % 5;
} else if (col1 == col2) {
row1 = (row1 + direction) % 5;
row2 = (row2 + direction) % 5;
} else {
int tmp = col1;
col1 = col2;
col2 = tmp;
}
text.setCharAt(i, charTable[row1][col1]);
text.setCharAt(i + 1, charTable[row2][col2]);
}
return text.toString();
}
}
and Transposition
import java.util.*;
import java.util.Scanner; // needed for Scanner
public class transpositionCipher
{
public static void main(String args[])
{
String key;
String message;
String encryptedMessage;
// Letters in the x-axis
int x=0;
// Letters in the y-axis
int y=0;
// Prompt the user
System.out.print( "Type your Key : " );
// Read a line of text from the user.
Scanner scan = new Scanner(System.in);
key = scan.nextLine();
// Display the input back to the user.
System.out.println( "Your Key is " + key );
//Prompt the user
System.out.print( "Type your Message : " );
//Read a line of text from the user.
message = scan.nextLine();
//Display the input back to the user.
System.out.println( "Your Message is " + message );
int msgchar = message.length();
int keycahr = key.length();
if (!((msgchar % keycahr) == 0)){
do{
message = message + "x";
msgchar = message.length();
}while(!((msgchar % keycahr) == 0));
}
encryptedMessage = "";
// To set the temp as [x][y]
char temp[][]=new char [key.length()][message.length()];
char msg[] = message.toCharArray();
// To populate the array
x=0;
y=0;
// To convert the message into an array of char
for (int i=0; i< msg.length;i++)
{
temp[x][y]=msg[i];
if (x==(key.length()-1))
{
x=0;
y=y+1;
} // Close if
else
{
x++;
}
} // Close for loop
// To sort the key
char t[]=new char [key.length()];
t=key.toCharArray();
Arrays.sort(t);
for (int j=0;j<y;j++)
{
for (int i=0;i<key.length();i++)
{
System.out.print(temp[i][j]);
}
System.out.println();
}
System.out.println();
// To print out row by row (i.e. y)
for (int j=0;j<y;j++){
// To compare the the sorted Key with the key
// For char in the key
for (int i=0;i<key.length();i++){
int pos=0;
// To get the position of key.charAt(i) from sorted key
for (pos=0;pos<t.length;pos++){
if (key.charAt(i)==t[pos]){
// To break the for loop once the key is found
break;
}
}
System.out.print(temp[pos][j]);
encryptedMessage+=temp[pos][j];
}
System.out.println();
}
System.out.println(encryptedMessage);
System.exit(0);
}enter code here
}
Take the output of one operation (PlayfairCipher.encode), which is the cyphertext and input it to the second operation (your transpositionial code) as it's plaintext.
Scanner sc = new Scanner(System.in);
String key = prompt("Enter an encryption key (min length 6): ", sc, 6);
String txt = prompt("Enter the message: ", sc, 1);
String jti = prompt("Replace J with I? y/n: ", sc, 1);
boolean changeJtoI = jti.equalsIgnoreCase("y");
PlayfairCipher.createTable(key, changeJtoI);
String enc = PlayfairCipher.encode(prepareText(txt, changeJtoI));
//Now instead of using 'message' for the second encryption, you use the output of the first operation 'enc'
int x=0;
int y=0;
int msgchar = enc.length();
int keycahr = key.length();
if (!((msgchar % keycahr) == 0)){
do{
enc = enc + "x";
msgchar = enc.length();
}while(!((msgchar % keycahr) == 0));
}
...

Count Occurrence of each letter in a loop and display with letter with the most number of occurences

I'm having trouble in using this code I found on the net. my goal is to count the number of times a letter show and display the letter with the most occurrence and if there are 2 or more letters that occurred at the same number of times then they will both show up.
This is my current output:
Current Output
Here is the code i found on the net and working with:
public void fcount(String str)
{
int[] occurence = new int[255];
// Scanner scanner = new Scanner(System.in);
// str = scanner.nextLine();
// optional to put eveyting in uppercase
str = str.toUpperCase();
// convert to char
char[] digit = str.toCharArray();
// count
for(int i = 0; i < digit.length; i++)
occurence[digit[i]]++;
// find max
int max = 0; // max value
char maxValue = 0; // max index
for(int i = 0; i < occurence.length; i++)
{
// new max ?
if(occurence[i] > max) {
max = occurence[i];
maxValue = (char) i;
}
}
// result
System.out.println("Character used " + max + " times is: " + (char) maxValue);
// return "";
}
And Here is the the loop where i'm using it:
public void calpha()
{
char startUpper = 'A';
String cones = null;
for (int i = 0; i < 12; i++) {
cones = Character.toString(startUpper);
System.out.println(startUpper);
}
fcount(cones);
}
There is an error in you loop:
cones = Character.toString(startUpper);
You are just re-assigning the value of cones, so fcount receives a string containing only the last character.
A solution is
cones += Character.toString(startUpper);
You have an issue in your int[] occurence = new int[255]; statement and usage: occurence[digit[i]]++ may lead to IndexOutOfBoundsException since char type is up to 2^16
Your code can not deal with non-ANSII characters. Mine does.
import java.util.*;
class Problem {
public static void main(String args[]) {
final String input = "I see trees outside of my window.".replace(" ", "");
final List<Character> chars = new ArrayList<>(input.length());
for (final char c : input.toCharArray()) {
chars.add(c);
}
int maxFreq = 0;
final Set<Character> mostFrequentChars = new HashSet<>();
for(final char c : chars) {
final int freq = Collections.frequency(chars, c);
if (freq > maxFreq) {
mostFrequentChars.clear();
mostFrequentChars.add(c);
maxFreq = freq;
}
else {
if (freq == maxFreq) {
mostFrequentChars.add(c);
}
}
}
for (Character c : mostFrequentChars) {
System.out.println(c);
}
}
}
Try this code:
public static void main(String[] args) throws IOException {
char startUpper = 'A';
String cones = "";
for (int i = 0; i < 12; i++) {
cones += Character.toString(startUpper);
System.out.println(startUpper);
}
fcount(cones);
}
public static void fcount(String str) {
HashMap<Character, Integer> hashMap = new HashMap<Character, Integer>();
HashSet<Character> letters = new HashSet<Character>();
str = str.toUpperCase();
//Assume that string str minimium has 1 char
int max = 1;
for (int i = 0; i < str.length(); i++) {
int newValue = 1;
if (hashMap.containsKey(str.charAt(i))) {
newValue = hashMap.get(str.charAt(i)) + 1;
hashMap.put(str.charAt(i), newValue);
if (newValue>=max) {
max = newValue;
letters.add(str.charAt(i));
}
} else {
hashMap.put(str.charAt(i), newValue);
}
}
System.out.println("Character used " + max + " times is: " + Arrays.toString(letters.toArray()));
// return "";
}

Char Arrays comparison

I am trying to build something like a hangman (for beginners)
I try this:
int i = 0;
int fails = 0;
boolean success = false;
boolean retval;
char[] defineword = new char[] { 'h', 'u', 'n', 'g' };
char[] givenchar = new char[0];
char[] testchar = new char[] { 'h' };
while (success == false && fails < 5) {
System.out.println("Give a char: ");
String word = input.next(); // INPUT STRING
givenchar = word.toCharArray(); // CONVERT
retval = Arrays.equals(givenchar, testchar);
System.out.println("THE LETTER IS " + retval);
if (retval == true) {
testchar[0] = defineword[i + 1];
} else {
fails++;
}
}
The problem is that it can't continue after the letter ('u'), it is stuck in 'u'.
One observation I will make is that you only real comparison is between givenchar, and testchar.
retval = Arrays.equals(givenchar, testchar);
It would make sense that this wouldn't work once you got past u because testchar never gets past u either. I think you might have intended to add an i++ somewhere.
testchar[0] = defineword[i + 1];
package mer;
import java.util.Scanner;
public class Aswe
{
int i=0;
int f=0;
boolean suc=false;
boolean ret;
char[] dw=new char[]{'h','u','n','g'};
char[] gc=new char[0];
char[] tc=new char[]{'h'};
Scanner i1;
public void me()
{
i1=new Scanner(System.in);
while(suc==false&&f<5)
{
System.out.println("give a char");
String ch=i1.nextLine();
gc=ch.toCharArray();
ret=eual(gc,tc);
System.out.println("the letter is"+ret);
if(ret)
{
tc[0]=dw[i+1];
}
else
f++;
}
}
public boolean eual(char[] a,char[] b)
{
if(a[0]==b[0])
return true;
else
return false;
}
public static void main(String ... args)
{
new Aswe().me();
}
}
private int fails = 0;
private final int maxFails = 5;
private char[] answer = new char[] {'j','a','v','a'};
public Hangman() {
Scanner scan = new Scanner(System.in);
/*
* Game Loop
*/
while(fails < maxFails){
System.out.print("Enter a char: ");
char givenChar = scan.next().charAt(0);
System.out.println("Given char is: " + Check(answer,givenChar));
}
}
/*
* Check if the char exists in the array.
*/
private boolean Check(char[] array,char value){
for(int i = 0; i < array.length; i++){
if(array[i] == value){
return true;
}
}
/*
* Okay did not find any char that match return false.
*/
return false;
}

how can i calculate the number of specific chars in a string?

Given a string how can i figure out the number of times each char in a string repeats itself
ex: aaaabbaaDD
output: 4a2b2a2D
public static void Calc() {
Input();
int count = 1;
String compressed = "";
for (int i = 0; i < input.length(); i++) {
if (lastChar == input.charAt(i)) {
count++;
compressed += Integer.toString(count) + input.charAt(i);
}
else {
lastChar = input.charAt(i);
count = 1;
}
}
System.out.println(compressed);
}
What you'r looking for is "Run-length encoding". Here is the working code to do that;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class RunLengthEncoding {
public static String encode(String source) {
StringBuffer dest = new StringBuffer();
// iterate through input string
// Iterate the string N no.of.times where N is size of the string to find run length for each character
for (int i = 0; i < source.length(); i++) {
// By default run Length for all character is one
int runLength = 1;
// Loop condition will break when it finds next character is different from previous character.
while (i+1 < source.length() && source.charAt(i) == source.charAt(i+1)) {
runLength++;
i++;
}
dest.append(runLength);
dest.append(source.charAt(i));
}
return dest.toString();
}
public static String decode(String source) {
StringBuffer dest = new StringBuffer();
Pattern pattern = Pattern.compile("[0-9]+|[a-zA-Z]");
Matcher matcher = pattern.matcher(source);
while (matcher.find()) {
int number = Integer.parseInt(matcher.group());
matcher.find();
while (number-- != 0) {
dest.append(matcher.group());
}
}
return dest.toString();
}
public static void main(String[] args) {
String example = "WWWWWWWWWWWWBWWWWWWWWWWWWBBBWWWWWWWWWWWWWWWWWWWWWWWWBWWWWWWWWWWWWWW";
System.out.println(encode(example));
System.out.println(decode("1W1B1W1B1W1B1W1B1W1B1W1B1W1B"));
}
}
This program first finds the unique characters or numbers in a string. It will then check the frequency of occurance.
This program considers capital and small case as different characters. You can modify it if required by using ignorecase method.
import java.io.*;
public class RunLength {
static BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
public static void main(String[] args) throws IOException {
System.out.println("Please enter the string");
String str = br.readLine();//the input string is in str
calculateFrequency(str);
}
private static void calculateFrequency(String str) {
int length = str.length();
String characters[] = new String[length];//to store all unique characters in string
int frequency[] = new int[length];//to store the frequency of the characters
for (int i = 0; i < length; i++) {
characters[i] = null;
frequency[i] = 0;
}
//To get unique characters
char temp;
String temporary;
int uniqueCount = 0;
for (int i = 0; i < length; i++) {
int flag = 0;
temp = str.charAt(i);
temporary = "" + temp;
for (int j = 0; j < length; j++) {
if (characters[j] != null && characters[j].equals(temporary)) {
flag = 1;
break;
}
}
if (flag == 0) {
characters[uniqueCount] = temporary;
uniqueCount++;
}
}
// To get the frequency of the characters
for(int i=0;i<length;i++){
temp=str.charAt(i);
temporary = ""+temp;
for(int j=0;i<characters.length;j++){
if(characters[j].equals(temporary)){
frequency[j]++;
break;
}
}
}
// To display the output
for (int i = 0; i < length; i++) {
if (characters[i] != null) {
System.out.println(characters[i]+" "+frequency[i]);
}
}
}}
Some hints: In your code sample you also need to reset count to 0 when the run ends (when you update lastChar). And you need to output the final run (after the loop is done). And you need some kind of else or continue between the two cases.
#Balarmurugan k's solution is better - but just by improving upon your code I came up with this -
String input = "aaaabbaaDD";
int count = 0;
char lastChar = 0;
int inputSize = input.length();
String output = "";
for (int i = 0; i < inputSize; i++) {
if (i == 0) {
lastChar = input.charAt(i);
count++;
} else {
if (lastChar == input.charAt(i)) {
count++;
} else {
output = output + count + "" + lastChar;
count = 1;
lastChar = input.charAt(i);
}
}
}
output = output + count + "" + lastChar;
System.out.println(output);

Categories