JAVA Input Comparison & Ignoring Negative Outcome - java

I'm new to JAVA and am struggling with a specific issue that I couldn't find an answer to so I decided to ask the good people of StackOverflow.
I am trying to build an ATM program. I have created an array of objects (The clients of the bank) with properties such as cardnumber, pin, balance, etc. And when any user will try and "log in" to the ATM he should type in his card number.
In the code below I tried to simulate the ATM going through the array of Clients and checking the input number with all the existing card numbers of each customer until it finds a match, and it works fine. The problem is that if it finds a match with client at position 10 it will display "Inexistent Card" 10 times before succeeding.
So I wanted to ask if there is a way for the program to ignore all these mismatches and only continue if it finds a match. And give me the "Inexistent Card" only when it finds 0 matches.
for (i = 0; i < clients.length; i++) {
if (input.equals(clients[i].accountnumber)) {
System.out.println("Welcome");
} else {
System.out.println("Inexistent Card");
}
}

consider using a found boolean variable
boolean found = false;
for (i = 0; i < clients.length; i++) {
if (input.equals(clients[i].accountnumber)) {
System.out.println("Welcome");
found = true;
break;
}
}
and then after the loop
if (!found) {
System.out.println("Inexistent Card");
}

That is exactly what you've written!
Think about it a bit more: You don't know the account doesn't exist until you've searched all the accounts and not found the one you want. You need to organise your code the same way. Just because clients[0] is not the one you are looking for, clients[1] might be, so you can't say "non existent" just yet...

The most simple way to achieve this:
int indexOfMatchingCard = -1;
for (... {
if (match) {
indexOfMatchingCard = current index
Afterwards, you can check if indexOfMatchingCard is >= 0; at the same time it tells you which of your cards matched. Just make sure to not reset that marker if you later find that other cards are not matching!
If you don't need to remember the matching index; you can use a simple boolean marker (which you initialize to false once; and change to true when on match).

Related

Is there a way to put a result from a loop, back into the same loop?

In my code, I am trying to filter out lines from a file that met conditions that are written by the user. A simple example would just be saying "red&round", and if written correctly, it would print out "apple". however, right now I am mentally stuck on how to simplify coding this. As of right now, I am only able to print out strings that match one condition, and I end up with either multiple of one string or strings that only match one condition. I feel like I know that I can just make another for loop within the for loop to filter it out eventually, but I feel like that would be a waste of time. Additionally, I have also tried to use while loops but I always ended up with infinite loops. This is my current code (only a snippet, where the main problem is). I am also just starting out in my first java course, and I would really appreciate any hints as to how I can make a simpler code for this problem.
if (args[1].contains("&")) {
String[] queryM = args[1].split("&");
for (int i = 0; i < queryM.length; i++) {
if (queryM[i].contains("not")) {
String command = queryM[i].substring(4, queryM[i].length() - 1);
if(run(lines.get(lineIndex), name(command), cond(command)) == false) {
System.out.println(lines.get(lineIndex));
}
}
else {
if(run(lines.get(lineIndex), name(queryM[i]), cond(queryM[i])) == true) {
System.out.println(lines.get(lineIndex));
}
}
}
}

Hangman that saves wrong guesses in array and prints them before each guess. also prints gameboard with "_" and correct guesses

so I've been studying Java for about 3 months and I am supposed to do a Hangman code using only arrays, loops, and if statements. the word to be guesses is read from another file and saved as a string. I have to be able to save the wrong guesses in an array. and after each guess print all the wrong guesses so far, as well as the gameboard with underscores for not guessed letters and the correct guesses of course in their place. here is my code so far :
for(int l = 0; l<wordlength;l++)
{
System.out.print("_");
}
System.out.println();
System.out.println("WRONG: ");
for(int c = 0; c<numofGuesses;c++)
{
System.out.println();
System.out.print("GUESS"+guessN+"/"+numofGuesses+": ");
char guess1=in.next().charAt(0);
char guess = Character.toUpperCase(guess1);
guessN = guessN+1;
for (int j = 0; j<wordlength;j++)
{
if (guess==guessword.charAt(j))
{
System.out.println("Great guess!");
System.out.print (guessword.charAt(j));
}
else
{
System.out.print("_");
WRONG[u]=guess;
u++;
}
}
if you guess A it prints correctly "A___" but then if you guess B after instead of printing "AB__" (the word to guess is ABLE) i get "B__" also the wrong array is not storing and printing all the wrong guesses each time. please help I've been trying for 5 days and that's all I did the entire day today and I couldn't get past this.
Because this sounds a lot like a homework assignment, I will give directions for solving this, but not provide a full working solution. Hopefully, seeing how one could1 go about approaching such a problem is enough of a step in the right direction to be able to solve it yourself.
Let's first think about what we need to do.
Read a word that needs to be guessed, say String toBeGuessed.
You did this. ✔
Keep track of the characters the player has guessed so far.
Keep track of the number of turns a player has gotten.
Keep track of if the word has been guessed (player won!).
Say that the number of guesses a player can make is fixed. This can be modeled using a constant:
/**
* Number of guesses a player can take.
*/
public static final int NUM_GUESSES = 10;
Now let's think about the main logic of our hangman game. It is good to first think about the structure of your program and only later actually implement it. When thinking of the program structure, we don't bother with specifics of the programming language of your choice yet. In pseudocode, it would be something like the following, maybe (let's indicate what you already have with ✔).
for turn from 1 upto NUM_GUESSES do ✔
show player what they guessed so far
show the gameboard
ask player for their new guess ✔
save player's guess and update internal state
check if the player won, let them know if they did
if player did not win
let them know
Right. So, we need to somehow store the guesses that a player made. Every guess is a character, and we know there will be at most NUM_GUESS guesses in total. A good option (and one that is suggested by your exercise) is an array!
/**
* Characters that have been guessed so far.
*/
private char[] guessed;
This can be initialized as follows, since we know the maximum number of guesses:
this.guessed = new char[NUM_GUESSES];
This gives us an array of NUM_GUESSES characters that are initialized to 0 (see here). Since users won't guess that character, we can use it to represent guesses that have not been done yet. Alternatively, we can keep track of the current turn of the player in a separate variable. Your choice!
In the following, I will not keep track of the current turn in a separate variable, just to show more of arrays and loops. It might be a fun exercise to change this to using an int turn variable!
show player what they guessed so far
Alright, this should be fairly straightforward now. We basically need to print the part of the guessed array that is not 0. That can be done using a loop, like so for example:
System.out.print("You so far guessed: ");
for (int i = 0; i < guessed.length; ++i) {
if (i > 0) {
System.out.print(", ");
}
if (guessed[i] != 0) {
System.out.print(guessed[i]);
} else {
break; // stop the loop as soon as we run into a 0
}
}
System.out.println(".");
This will print something like You so far guessed: a, b, c. when the player guessed those characters. See how we only print the comma when some other character was printed before?
show the gameboard
The next point of the program structure is trickier to get right. Let's think a bit about structure again.
for each character in toBeGuessed
if the character has been guessed
print it
else
print an underscore
Looping over every character of a word can be done as follows.
int length = toBeGuessed.length();
for (int i = 0; i < length; ++i) {
char character = toBeGuessed.charAt(i);
// do something with character here
}
How do you find if a character has been guessed yet? Well, by checking if it is stored in the guessed array. This again can be done using a loop. That loop will be very similar to the one we have written above, when showing what the player guessed so far. I think you should be able to figure that one out.
save player's guess and update internal state
We move on to the next point of the program structure. Say that we have a char guess that the player guessed. We need to store this in our array guessed. Where? Well, at the first open spot, that seems a reasonable choice. To find that one, let's use a loop again, and break the loop when we have found an open spot.
for (int i = 0; i < guessed.length; ++i) {
if (guessed[i] == 0) {
guessed[i] = guess;
break;
}
}
check if the player won, let them know if they did
What we need to know in order to see if the player won, is simply if the number of characters they guessed right is equal to the number of characters in toBeGuessed. You could modify the loop for showing the gameboard to not print characters, but count correct ones. Then at the end compare to toBeGuessed.length() and if they are equal, the player won.
if player did not win, let them know
This should be fairly easy, if you got the previous point working.
When you did all the above and stitched it together, you should have a working version of hangman. Your very own, something to be proud of!
Some tips and tricks:
you can implement most of the points described above as separate methods;
when you do so, you can write one main method that calls the other methods (this will make it easier to read your own code and make changes to it);
try to put as little code as possible in the main method.
Here is a little template that you can start from.
import java.io.PrintStream;
import java.util.Scanner;
public class HangMan
{
/** Number of guesses a player can take. */
public static final int NUM_GUESSES = 10;
/** Word to be guessed in a game of hangman. */
private String toGuess;
/** Letters that have been guessed so far. */
private char[] guessed;
/**
* Construct a new game of hangman, ready to be played.
*/
public HangMan(String toGuess)
{
this.toGuess = toGuess;
this.guessed = new char[NUM_GUESSES];
}
// your other methods go here
/**
* Read guesses from given input and print results to given output.
* Continues until guesses have run out, or word was guessed.
*/
public void play(Scanner in, PrintStream out)
{
for (int round = 0; round < NUM_GUESSES; ++round) {
showGuessedSoFar(out);
showGameBoard(out);
char guess = askGuess(in, out);
saveGuess(guess);
if (hasPlayerWon()) {
out.println("You won!");
return;
}
}
// at this point, player ran out of guesses and hence lost
out.println("You lost...");
}
/**
* The bit that runs our hangman game.
*/
public static void main(String[] args)
{
// read word to guess from arguments, with a default value
// you would probably insert your "read word from file" code here
HangMan game = new HangMan(args.length >= 1 ? args[0] : "ABLE");
// play a game, using system input and output
game.play(new Scanner(System.in), System.out);
}
}
Good luck!
TL;DR. Trying to teach one how to think about a problem and how to write code that executes the solution one thought of. Features some example code with arrays and loops.
1 This is only one possible solution, there are always many ways to solve a given problem.

How to continue looping through DataInputStream?

I am reading a binary file and I have to parse through the headers in this file.
I have a DataInputStream set up and I need to get it to continue looping through the file until the end. I am new to Java so not sure how I would carry this over from my C# experience. At the moment I have the following code:
while (is.position != is.length) {
if ( card == Staff) {
System.out.print(card);
} else if ( card == Student ) {
System.out.print(card);
} else if (card == Admin) {
System.out.print(card);
} else {
System.out.print("Incorrect");
}
}
is is the input stream I created, the only error I have is in the first line where the while loop starts under position and length it says they cannot be resolved or is not a field.
Looking at the docs it doesn't look like DataInputStream has a position field. You could possibly use one of the other methods to check whether there is more data available, but it's not clear from your code sample what you're trying to do.
At present there are a number of issues I can see with your code:
If card, Staff, Student and Admin are of type String, then you need to compare them using the equals(String s) method, not the == reference equality (ie. card.equals(Staff) rather than card == Staff)
You don't seem to iterate in your loop. If you don't do anything to change the value of is.position (I know this doesn't actually exist, but hypothetically speaking...) then if you can enter the loop you'll never leave it.
You don't change the value of card. If you do iterate some fixed number of times, you're going to just have identical output printed over and over again, which probably isn't what you intended.

Java Error When attempting to use the return from a method as an item in an if statement

I keep getting the following errors:
Cannot find symbol
Variable find
cannot find symbol
method getdata(int)
I am sure I am making this way more difficult than it is, but I am not sure how make this work so that the return from searching through the array, can be seen and evaluated by the if statement.
//assigns manager identification
manID = keyboard.nextInt();
//Fibonacci binary array for passwords
int[] passWArray = {00000000,00000001,00000001,00000010,00000011,00000101,00001000,00001101};
//item = find.getdata(manID);
if (getdata(manID) != -1)
{
//Do work here
dblPayRate = 10.85;
dblGrossPay = (intHours * dblPayRate) + (15.00);
dblTaxes = dblGrossPay * 0.19;
dblGrossPay -= dblTaxes;
//Print information to user
System.out.print("\n\n$" + df2.format(dblTaxes) +
" was withheld from this paycheck in taxes after working "+ intHours + " hours.\n\n");
System.out.print("The amount \"Employer Here\" owes you is $" + df2.format(dblGrossPay) + "\n");
}
else
{
// Dialog box for incorrect password
JOptionPane.showMessageDialog(null, "Invalid Entry! Contact the BOFH!");
//exits program (Note: needed for any JOptionPane programs)
System.exit(0);
}
}// end of long if statement for >50 hours
}//end of main method
public int find(int[] passWArray, int manID)
{
//search for manID in passWArray array
for (int index = 0; index < passWArray.length; index++)
if ( passWArray[index] == manID )
return manID;
//-1 indicates the value was not found
return -1;
}// end of find method
Change
if (getdata(manID) != -1)
into
if (find(passWArray , manID) != -1)
BTW those numbers don't magically become binary because they only contain 0's and 1's. Here's a hint:
int thirteen = Integer.parseInt("00001101", 2)
EDIT: in response to your next error
For now make the method static:
public static int find(int[] passWArray, int manID)
Eventually you might want to think about your 'Object-Oriented design' and just use the main() method as an entry point. Within main you create an instance of a class and let it do its work. In this way you can use the powers of O-O like encapsulation and inheritance and don't have to make everything static.
EDIT2: Afterthought
Your program seems to have the following 'actions':
user interaction
authentication
calculation
And there seem to be the following 'things' in your domain:
user
password
keyboard
display (command line and screen)
calculation
A good rule of thumb for an O-O design is to convert some of the 'things' and 'actions' already present in your domain into classes. A good class has a single responsibility and shares as little as possible of its data and methods with other classes (this is called information hiding).
Here's a class diagram that comes to mind:
User (represents a user, contains a single field 'password')
Authenticator (authenticates a user, contains the list of allowed passwords)
Console (all user interaction, either use System.out/in or Swing, but don't mix them)
Calculator (it calculates shit)

Javabat substring counting

public boolean catDog(String str)
{
int count = 0;
for (int i = 0; i < str.length(); i++)
{
String sub = str.substring(i, i+1);
if (sub.equals("cat") && sub.equals("dog"))
count++;
}
return count == 0;
}
There's my code for catDog, have been working on it for a while and just cannot find out what's wrong. Help would be much appreciated!*/
EDIT- I want to Return true if the string "cat" and "dog" appear the same number of times in the given string.
One problem is that this will never be true:
if (sub.equals("cat") && sub.equals("dog"))
&& means and. || means or.
However, another problem is that your code looks like your are flailing around randomly trying to get it to work. Everyone does this to some extent in their first programming class, but it's a bad habit. Try to come up with a clear mental picture of how to solve the problem before you write any code, then write the code, then verify that the code actually does what you think it should do and that your initial solution was correct.
EDIT: What I said goes double now that you've clarified what your function is supposed to do. Your approach to solving the problem is not correct, so you need to rethink how to solve the problem, not futz with the implementation.
Here's a critique since I don't believe in giving code for homework. But you have at least tried which is better than most of the clowns posting homework here.
you need two variables, one for storing cat occurrences, one for dog, or a way of telling the difference.
your substring isn't getting enough characters.
a string can never be both cat and dog, you need to check them independently and update the right count.
your return statement should return true if catcount is equal to dogcount, although your version would work if you stored the differences between cats and dogs.
Other than those, I'd be using string searches rather than checking every position but that may be your next assignment. The method you've chosen is perfectly adequate for CS101-type homework.
It should be reasonably easy to get yours working if you address the points I gave above. One thing you may want to try is inserting debugging statements at important places in your code such as:
System.out.println(
"i = " + Integer.toString (i) +
", sub = ["+sub+"]" +
", count = " + Integer.toString(count));
immediately before the closing brace of the for loop. This is invaluable in figuring out what your code is doing wrong.
Here's my ROT13 version if you run into too much trouble and want something to compare it to, but please don't use it without getting yours working first. That doesn't help you in the long run. And, it's almost certain that your educators are tracking StackOverflow to detect plagiarism anyway, so it wouldn't even help you in the short term.
Not that I really care, the more dumb coders in the employment pool, the better it is for me :-)
choyvp obbyrna pngQbt(Fgevat fge) {
vag qvssrerapr = 0;
sbe (vag v = 0; v < fge.yratgu() - 2; v++) {
Fgevat fho = fge.fhofgevat(v, v+3);
vs (fho.rdhnyf("png")) {
qvssrerapr++;
} ryfr {
vs (fho.rdhnyf("qbt")) {
qvssrerapr--;
}
}
}
erghea qvssrerapr == 0;
}
Another thing to note here is that substring in Java's built-in String class is exclusive on the upper bound.
That is, for String str = "abcdefg", str.substring( 0, 2 ) retrieves "ab" rather than "abc." To match 3 characters, you need to get the substring from i to i+3.
My code for do this:
public boolean catDog(String str) {
if ((new StringTokenizer(str, "cat")).countTokens() ==
(new StringTokenizer(str, "dog")).countTokens()) {
return true;
}
return false;
}
Hope this will help you
EDIT: Sorry this code will not work since you can have 2 tokens side by side in your string. Best if you use countMatches from StringUtils Apache commons library.
String sub = str.substring(i, i+1);
The above line is only getting a 2-character substring so instead of getting "cat" you'll get "ca" and it will never match. Fix this by changing 'i+1' to 'i+2'.
Edit: Now that you've clarified your question in the comments: You should have two counter variables, one to count the 'dog's and one to count the 'cat's. Then at the end return true if count_cats == count_dogs.

Categories

Resources