I just started with Java and to learn it I was trying to program a Tamagotchi in BlueJ. This is an extract of the code:
public class Tamagotchi
{
private int hunger;
private int mood;
private int fatigue;
private int hBorder;
private int mBorder;
private int fBorder;
private String generalCondition;
public Tamagotchi(int hungerBorder, int moodBorder, int fatigueBorder)
{
// Instanzvariable initialisieren
hunger = 0;
mood = 0;
fatigue = 0;
hBorder = hungerBorder;
mBorder = moodBorder;
fBorder = fatigueBorder;
generalCondition = "indifferent";
}
public void setGeneralCondition(){
if (fatigue > fBorder){
generalCondition = "tired";
}
if ((fatigue < fBorder) & (hunger > hBorder)){
generalCondition = "hungry";
}
if ((mood > mBorder) & (hunger < hBorder) &
(fatigue < fBorder)){
generalCondition = "happy";
}
else {
generalCondition = "indifferent";
}
}
public void play()
{
if (hunger > hBorder){hunger += 2; mood += 2; fatigue += 3;
}
else {}
setGeneralCondition();
}
public void eat(){
if (fatigue > fBorder){hunger -= 2; fatigue += 2;
}
else{}
setGeneralCondition();
}
public void sleep(){
if (hunger > hBorder){hunger += 1; mood -= 1; fatigue = 0;
}
else{hunger += 1; mood += 1; fatigue = 0;
}
setGeneralCondition();
}
public void pet(){
hunger += 1;
mood += 2;
setGeneralCondition();
}
public String getGentralCondition(){
return generalCondition;
}
public void makeHappy(){
eat();
sleep();
}
}
My problem is that the generalCondition does not change when I use any of the methods. I think something with the method setGeneralCondition is wrong but I don't know where the problem is. Can somebody help :/ ?
THX in advance.
EDIT:
I posted the hole code now. As I said in the comment: I want the generalCondition to change whenever I use a method like eat(), play()...
The method setGeneralCondition was supposed to check if one of the values hunger mood or fatigue passes a certain border and change the Condition (to tired, hungry or happy). But whenever I use one of the other methods the generalCondition doesn't change.
EDIT: I have made further edits to your code and have come up with a little main that runs your code and changes generalCondition! Check it out and run it for yourself to see.
My intuition tells me this class Tamagotchi is a class file or an object Tamagotchi that will be used by a main method that rests somewhere in another file. If that is the case, I believe it is a simple fix and all you need to do is add this. in a lot of places. I have gone ahead and done just that for you below. Try this and let me know if this works!
public class Tamagotchi{
private int hunger;
private int mood;
private int fatigue;
private int hungerBorder;
private int moodBorder;
private int fatigueBorder;
private String generalCondition;
public Tamagotchi(int hungerBorder, int moodBorder, int fatigueBorder)
{
// Instanzvariable initialisieren
this.hunger = 30;
this.mood = 30;
this.fatigue = 30;
this.hungerBorder = hungerBorder;
this.moodBorder = moodBorder;
this.fatigueBorder = fatigueBorder;
this.generalCondition = "indifferent";
}
public void setGeneralCondition(){
if (fatigue > fatigueBorder){
this.generalCondition = "tired";
return;
}
if ((fatigue < fatigueBorder) && (hunger > hungerBorder)){
this.generalCondition = "hungry";
return;
}
if ((mood > moodBorder) && (hunger < hungerBorder) && (fatigue < fatigueBorder)){
this.generalCondition = "happy";
return;
} else {
this.generalCondition = "indifferent";
}
}
public String getGeneralCondition(){
return generalCondition;
}
public void play()
{
if (!generalCondition.equalsIgnoreCase("hungry")){
hunger += 2; mood += 2; fatigue += 3;
} else {
}
setGeneralCondition();
}
public void eat(){
if (fatigue > fatigueBorder){
hunger -= 2; fatigue += 2;
} else{
}
setGeneralCondition();
}
public void sleep(){
if (hunger > hungerBorder){
hunger += 1; mood -= 1; fatigue = 0;
} else{
hunger += 1; mood += 1; fatigue = 0;
}
setGeneralCondition();
}
public void pet(){
hunger += 1;
mood += 2;
setGeneralCondition();
}
public void makeHappy(){
eat();
sleep();
}
}
Here is a little main method I wrote to test the code above.
public class Test {
public static void main(String[] args) {
Tamagotchi test = new Tamagotchi(10, 10, 10);
test.play();
test.makeHappy();
System.out.println(test.getGeneralCondition());
}
}
Output :
hungry
Hope this helps!
P.S. here is a link to basic coding styles. Practice coding with these styles as it makes your code easier to read for others, yourself, it looks a lot cleaner, and it is easier to see and fix errors! Coding Style Guide
There are few major problems with the code that you posted.
As sloughy stated, you need to add "this" to hungerBorder, moodBorder, and fatigueBorder in the Tamagotchi constructor. What you are currently doing is setting the PARAMETERS hungerBorder, moodBorder and fatigueBorder to themselves. When you add "this" in front of a variable, you are now referencing the class variable regardless of whatever local variables you are currently working with.
Additionally, you shouldn't compare Strings with == and !=. This will only work when both strings in the comparison are pointing to the same internal reference. Instead you should use .equals() which can be called like this:
String testString = "test";
String otherString = "other";
if (testString.equals(otherString)) {
System.out.println("equal");
} else {
System.out.println("not equal");
}
This is working code from compilation perspective. The problem you've met is probably in data or logic you implemented. To get generalCondition changed you need condition
((mood > mBorder) & (hunger < hBorder) & (fatigue < fBorder)) to return true otherwise you'll set same default value.
Few tips:
Most probably you didn't debug your app. Start doing this especially when you new in programming/java.
Use && instead of & short. In 99% of usage this in if clause it's better (with time you'll know why)
Related
hello guys for simulating the queue blocking time for an M/M/1 I came up with this very solution, but it is not Object-oriented unfortunately, also the problem is I want to simulate it with M/M/2 system,for instance I initialized lambda with 19 and mu with 20 just for ease up the calculation any solution, hint, code example will be greatly appreciated.
public class Main {
public static void main(String[] args) {
final int MAX_ENTITY = 100000;
final int SYSTEM_CAPACITY = 5;
final int BUSY = 1;
final int IDLE = 0;
double lambda = 19, mu = 20;
int blocked = 0;
int queue_length = 0;
int server_state = IDLE;
int entity = 0;
double next_av = getArivalRand(lambda);
double next_dp = next_av + getDeparturedRand(lambda);
while (entity <= MAX_ENTITY) {
//Arrival
if (next_av <= next_dp) {
entity++;
if (server_state == IDLE) {
server_state = BUSY;
} else if (queue_length < SYSTEM_CAPACITY - 1) {
queue_length++;
} else {
blocked++;
}
next_av += getArivalRand(lambda);
} // Departure
else if (queue_length > 0) {
queue_length--;
next_dp = next_dp + getDeparturedRand(mu);
} else {
server_state = IDLE;
next_dp = next_av + getDeparturedRand(mu);
}
}
System.out.println("Blocked Etity:" + blocked + "\n");
}
public static double getArivalRand(double lambda) {
return -1 / lambda * Math.log(1 - Math.random());
}
public static double getDeparturedRand(double mu) {
return -1 / mu * Math.log(1 - Math.random());
}
}
EDIT:
check here if u don't know about the queue theory
oh boy you're code needs serious refactoring in order to achieve M/M/2.
I created a gist file here which I think implements what you wanted,
In the gist file I created a Dispatcher class for balancing two queues in two servers and also I've simulated it with two seeds, it is much more Object-Oriented approach,
here is an example code from gist file which is for balancing load of
the tasks
if (server1.getQueueLength() < server2.getQueueLength())
currentServer = server1;
else if (server1.getQueueLength() > server2.getQueueLength())
currentServer = server2;
else if (currentServer == server1)
currentServer = server2;
else
currentServer = server1;
I have been buried in this assignment for 2 days chasing down rabbit holes for possible solutions. I am beginner Java, so I am sure this shouldn't be as difficult as I am making it.
I trying to program the infamous Java Bean Machine... My professor want the Class Path to return a String Variable that only holds "R" "L" . to represent the path of the dropped ball.
Each ball should have its own Path... I can get the path... but I can not get the path to print in a string outside of the for/if statement.
Here are his instructions... in case you can see if I am interpreting this incorrectly.
Please help!! Thank you in advance for sifting through this....
my code so far ******** i have updated the code to reflect the suggestions.. Thank you... ***************** New problem is it repeats the series of letters in a line... I only need a string of 6 char ....(LRLLRL)
public class Path {
StringBuilder myPath;
public Path() {
myPath = new StringBuilder();
}
void moveRight() {
myPath.append("R");
}
void moveLeft() {
myPath.append("L");
}
public void fallLevels(int levels) {
levels = 6;
for (int i = 0; i < (levels); i++) {
if (Math.random() < 0.5) {
this.moveRight();
} else {
this.moveLeft();
}
}
}
public String getPath() {
System.out.print(myPath.toString());
return myPath.toString();
}
}
}
******Thank you all.. this class now returns the correct string for one ball...***************
here is my code so far for multiple balls... I can get a long continuous string of 6 character sequences... I need each sequence to be a searchable string...I am not sure if I need to alter the Path class or if its something in the simulateGame() method. I think I can take it after this hump... Thank you again....
public class BeanMachine {
int numberOfLevels;
int[] ballsInBins;
Path thePath = new Path();
public BeanMachine(int numberOfLevels) {
this.numberOfLevels = 6;
ballsInBins = new int[this.numberOfLevels + 1];
// this.numberOfLevels +
}
public void simulateGame(int number) {
//looping through each ball
for (int i = 0; i < numberOfLevels -1; i++) {
thePath.fallLevels(0);
}
thePath.getPath().toString();
}
*** this isn't the entire code for this class... I have to get this method correct to continue....
Problem with your code:
if (Math.random() < 0.5) {
**loop = this.myPath = "R";**
} else {
**loop = this.myPath ="L";**
}
Change this to:
if (Math.random() < 0.5) {
**loop = this.myPath + "R";**
} else {
**loop = this.myPath + "L";**
}
Just added ** to highlight where there is wrong in your code
I am aware there are multiple threads like my assignment below, but I just can't figure it out. I can't exactly figure out the mistake. Help would be appreciated.
I am trying to do this program:
Everything works fine unless I input the same chains or similar (for example ACTG and ACTG or ACTG and ACTGCCCC), when it tells me
string index out of range
This is that part of my code:
int tries=0;
int pos=-1;
int k;
for (int i=0; i<longDNA.length(); i++) {
tries=0;
k=i;
for (int j=0; j<shortDNA.length(); j++) {
char s=shortDNA.charAt(j);
char l=longDNA.charAt(k);
if (canConnect(s,l)) {
tries+=1;
k+=1;
}
}
if (tries==shortDNA.length()-1) {
pos=i-1;
break;
}
}
Let's call the two DNA strings longer and shorter. In order for shorter to attach somewhere on longer, a sequence of bases complementary to shorter must be found somewhere in longer, e.g. if there is ACGT in shorter, then you need to find TGCA somewhere in longer.
So, if you take shorter and flip all of its bases to their complements:
char[] cs = shorter.toCharArray();
for (int i = 0; i < cs.length; ++i) {
// getComplement changes A->T, C->G, G->C, T->A,
// and throws an exception in all other cases
cs[i] = getComplement(cs[i]);
}
String shorterComplement = new String(cs);
For the examples given in your question, the complement of TTGCC is AACGG, and the complement of TGC is ACG.
Then all you have to do is to find shorterComplement within longer. You can do this trivially using indexOf:
return longer.indexOf(shorterComplement);
Of course, if the point of the exercise is to learn how to do string matching, you can look at well-known algorithms for doing the equivalent of indexOf. For instance, Wikipedia has a category for String matching algorithms.
I tried to replicate your full code as fast as I could, I'm not sure if I fixed the problem but you don't get any errors.
Please try it and see if it works.
I hope you get this in time and good luck!
import java.util.Arrays;
public class DNA {
public static void main(String[] args) {
System.out.println(findFirstMatchingPosition("ACTG", "ACTG"));
}
public static int findFirstMatchingPosition(String shortDNA, String longDNA) {
int positionInLong = 0;
int positionInShort;
while (positionInLong < longDNA.length()) {
positionInShort = 0;
while(positionInShort < shortDNA.length()) {
String s = shortDNA.substring(positionInShort, positionInShort + 1);
if(positionInShort + positionInLong + 1 > longDNA.length()) {
break;
}
String l = longDNA.substring(positionInShort + positionInLong, positionInShort + positionInLong + 1);
if(canConnect(s, l)) {
positionInShort++;
if(positionInShort == shortDNA.length()) {
return positionInLong;
}
} else {
break;
}
}
positionInLong++;
if(positionInLong == longDNA.length()) {
return -1;
}
}
return -1;
}
private static String[] connections = {
"AT",
"TA",
"GC",
"CG"
};
private static boolean canConnect(String s, String l) {
if(Arrays.asList(connections).contains((s+l).toUpperCase())) {
return true;
} else {
return false;
}
}
}
I finally changed something with the k as Faraz had mentioned above to make sure the charAt does not get used when k overrides the length of the string and the program worked marvelously!
The code was changed to the following:
int tries=0;
int pos=-1;
int k;
for (int i=0; i<longDNA.length(); i++) {
tries=0;
k=i;
for (int j=0; j<shortDNA.length(); j++) {
if (k<longDNA.length()) {
char s=shortDNA.charAt(j);
char l=longDNA.charAt(k);
if ((s=='A' && l=='T') || (s=='T' && l=='A') || (s=='G' && l=='C') || (s=='C' && l=='G')) {
tries+=1;
k+=1;
}
}
}
if (tries==shortDNA.length()) {
pos=i;
break;
}
}
I am not sure how aesthetically pleasing or correct this excerpt is but - it completely solved my problem, and just 2 minutes before the deadline! :)
A huge thanks to all of you for spending some time to help me!!
I am writing on a method which should analyse a polynomial given by the user (as String) and do different stuff with it in the future. At the moment, I was trying to test the code I have so far but whenever I execute the program, it freezes and after sitting for hours in front of the computer I still can't find the culprit in it.
I was testing if a polynomial of one variable could be analysed and then re-printed, but it doesn't work.
I hoped anyone could help me out on this.
Here's the code block in the main which executes the method, the string userInput is a polynomial (e.g 4x-6x^2):
String userInput = inputArea.getText().trim();
Monomials monomials = new Monomials();
monomials.analyse(userInput);
Here's the class monomials with its method analyse():
//Class Monomial
class Monomials
{
private int coeff = 0;
private char var;
private int addpow = 1;
private int pow;
private char powsign = '^';
private char minus = '-';
private boolean isnegative = false;
private String mono;
StringBuilder stringBuilder = new StringBuilder();
public int getCoeff(int coeff)
{
return coeff;
}
public void setCoeff(int coeff)
{
this.coeff = coeff;
}
public void setVar(char var)
{
this.var = var;
}
public void setPow(int pow)
{
this.pow = pow;
}
public String getMono(String monomials)
{
return mono;
}
// Method to further analyse user's input.
public void analyse(String polynomial)
{
//Split the poynomial into monomials and store them in an array list.
polynomial = polynomial.replaceAll("-","+-");
String polyParts[] = polynomial.split("\\+");
ArrayList<String> monomials = new ArrayList<String>(Arrays.asList(polyParts));
// Iterate the monomials.
for (int i = 0; i <= monomials.size(); i++)
{
String monomial = monomials.get(i);
// Analyse the monomial.
for (int x = 0; x <= monomial.length(); x++)
{
char c = monomial.charAt(x);
int countcoeff = 0;
int countvar = 0;
// check if negative.
if (c == minus)
{
isnegative = true;
x++;
}
// get the coefficient.
if (Character.isDigit(c))
{
while (Character.isDigit(c))
{
countcoeff++;
x++;
}
if (isnegative)
{
setCoeff(Integer.parseInt(monomial.substring(1, countcoeff)));
} else
{
setCoeff(Integer.parseInt(monomial.substring(0, countcoeff)));
}
}
// get the variable.
if (Character.isLetter(c))
{
char var = c;
while (Character.isLetter(var))
{
countvar++;
addpow++;
x++;
}
}
// get the power.
if (c == powsign)
{
countvar++;
x++;
while (Character.isDigit(c))
{
x++;
}
if (isnegative)
{
setPow(Integer.parseInt(monomial.substring(countcoeff+countvar+2, x)));
} else
{
setPow(Integer.parseInt(monomial.substring(countcoeff+countvar+1, x)));
}
pow += addpow;
}
}
if (isnegative)
{
stringBuilder.append(String.valueOf(minus));
}
stringBuilder.append(String.valueOf(coeff) + String.valueOf(var) + String.valueOf(powsign) + String.valueOf(pow));
mono = stringBuilder.toString();
monomials.set(i, mono);
}
for (int i = 0; i < monomials.size(); i++)
{
System.out.println(String.valueOf(monomials.get(i)));
}
} // End of method analyse().
} // End of class Monomial
You have a couple of loops which will never exit:
while (Character.isDigit(c))
{
countcoeff++;
x++;
}
How to find out Stuff like that?
If you use Eclipse, you can run your Code in Debug Mode, switch to the debug-perspective and click on the yellow Suspend-Symbol. That will suspend your Program, in the Debug-View you can see in which line the Thread is "hanging", if you click on it it will open the source-code.
If you don't use an IDE with that function, you can use the JDK-Tools: Use jps to find out the ID of your program:
C:\jdk\jdk8u45x64\jdk1.8.0_45\bin>jps
7216
5688 Jps
6248 Monomials
Then use jstack to print a stack trace of all running threads:
C:\jdk\jdk8u45x64\jdk1.8.0_45\bin>jstack 6248
[other threads omitted]
"main" #1 prio=5 os_prio=0 tid=0x000000000203e800 nid=0x1b2c runnable [0x000000000201e000]
java.lang.Thread.State: RUNNABLE
at Monomials.analyse(Monomials.java:77)
at Monomials.main(Monomials.java:10)
one of your loop is running infinitely. You should replace it with if condition.
while (Character.isDigit(c))
{
countcoeff++;
x++;
}
replace it with
if (Character.isDigit(c))
{
countcoeff++;
x++;
}
Or you could use break statement here.
As the others stated already
while (Character.isDigit(c))
is your problem.
But you have that two times not one time, so both are a problem. The 2nd isn't a real problem, because Character.isDigit and if (c == powsign) canĀ“t be both true at the same time, so the 2nd inifit loop never gets executed, which brings me to the next point: bugs.
In your code there are a tremendous amount of them :-D
Both for loops are running to far (<= .size() & <= .length()), replace <= with <.
Also, the x++ placed around in your code are wrong. x gets incremented automaticially and if you want to exit the loop early, use break; or use continue; if you want to jump to the next iteration early.
The for loop in the backEnd class - CompareGuess method is not working.
....................................................................................................................................................
public class frontEnd
{
public static void main (String args[])
{
int GetGuess = 0;
backEnd e1 = new backEnd();
e1.InitializeArray();
while(e1.chanceCounter<3)
{
System.out.println("Enter a number");
GetGuess = (int)(Math.random()*6);
System.out.println(GetGuess);
e1.UserGuess(GetGuess);
e1.CompareGuess();
if(e1.suc!=1)
{
System.out.println("It is a miss");
}
}
System.out.println("Sorry, no chances left");
}
}
class backEnd
{
int Guess;
int HitCounter=0;
int[] abc = new int[7] ;
int chanceCounter=0;
int suc = 0;
int x =0;
public void InitializeArray()
{
abc[1]= 3;
abc[2] = 5;
abc[4] = 1;
}
public void UserGuess(int guess)
{
Guess = guess;
}
public void CompareGuess()
{
for(x=0; x<=6; x++ )
{
if (abc[x] == Guess)
{
System.out.println("It is a hit");
chanceCounter = chanceCounter + 1;
suc = 1;
}
break;
}
}
}
The problems seems to be here:
for(x=0; x<=6; x++ )
{
if (abc[x] == Guess)
{
System.out.println("It is a hit");
chanceCounter = chanceCounter + 1;
suc = 1;
}
break; //Here
}
Look what your code does:
Your for loop makes the first iteration, taking x = 0
If abc[x] it's equals to Guess then your program executes the code inside the if statement. After, the break statement will be executed.
If not, it just execute the break statement
So, in both cases, the break statement it's going to be executed in the first iteration (therefore, your program will go out of the for loop).
Look that your program only will execute your first iteration but not the rest (x = 1, x = 2 [....] x =6).
If you want that your for loop go through all the iterations you have to remove your break statement from your code.
I expect it will be helpful for you!
Since your game is all about guessing. I took a guess at what it's supposed to do then I rewrote your code, because I couldn't bear to leave it as it was. I left it as similar to your as I can cope with:
public class FrontEnd
{
public static void main (String args[])
{
int getGuess = 0;
BackEnd e1 = new BackEnd();
e1.initializeArray();
int totalChances = 3;
while(e1.chanceCounter < totalChances)
{
System.out.println("Enter a number");
getGuess = (int)(Math.random()*6);
System.out.println(getGuess);
e1.userGuess(getGuess);
e1.compareGuess();
if(!e1.suc)
{
System.out.println("It is a miss");
}
e1.suc = false;
e1.chanceCounter++;
}
System.out.println("Sorry, no chances left");
System.out.println("you scored " + e1.hitCounter + " out of " + totalChances);
}
}
class BackEnd
{
int guess;
int hitCounter = 0;
int[] abc = new int[7] ;
int chanceCounter = 0;
boolean suc = false;
public void initializeArray()
{
abc[1] = 3;
abc[2] = 5;
abc[4] = 1;
}
public void userGuess(int guess)
{
this.guess = guess;
}
public void compareGuess()
{
for( int x = 0; x <= 6; x++ )
{
if (abc[x] == guess)
{
System.out.println("It is a hit");
hitCounter++;
suc = true;
break;
}
}
}
}
As others have said the break statement is supposed to be inside the conditional block. Also it looks like you were forgetting to reset the suc variable after each guess. Also you weren't using hitCounter at all. I assumed it's for counting correct guesses, which left me wondering when to update chanceCounter: either after each guess or after each wrong guess. I didn't know if the guesser was supposed to run out of chances after 3 guesses, or after 3 wrong guesses. I went with the former and update the chanceCounter after every guess.
guesses of 0 are considered correct because they match with all the entries in the abc array that are not initialised.