Calculate pi to the nth term with leibiniz sequence - java

Hey I have to create a method where I have to calculate pi to a passed term (a) using the leibiniz sequence. This is what I have so far
public static double calculatePi(int a){
double oddNum=1;
double pi=0;
for(int x=0; x<a; x++){
if(x%2==0)
pi=pi+(4/oddNum);
else
pi=pi-(4/oddNum);
oddNum=oddNum+2;
}
return pi;
}
I also need help writing a method that accepts a passed string and a (x)term. In the method it will add a "#" every x letters. So if its passed (sundae, 2) it will return su#nd#ae#. I have most of it down but theres a logical error that doesnt allow something like (cats, 3) to compile.
public static String addPounds(String s, int x){
String a="";
for(int i=0; i<s.length(); i=i+x){
a=(a+s.substring(i,i+x)+"#");
}
return a;
}
Thanks so much!

Your pi method is working fine.
You should change the other one to this. I have written it a little bit different so you get the logic easily.
public static String addPounds(String s, int x){
String a = "";
//starting from 1 so i can do mod division easily
for(int i = 1; i <= s.length(); i++){
//check if next # has to be placed at the end
if(i + 1 > s.length() && (i + 1) % x == 0){
a += "#";
//check if next # has to be placed somewhere inside the string
}else if(i % x == 0){
a += s.charAt(i - 1);
a += "#";
//oherwise just add the char at i-1
}else {
a += s.charAt(i - 1 );
}
}
return a;
}

Your addPounds method throws a StringIndexOutOfBoundsException with your given example (cats,3).
for(int i=0; i<s.length(); i=i+x){
a=(a+s.substring(i,i+x)+"#");
}
In the first execution of this for-loop, your variable 'a' will correctly be "Cat#". But now it goes wrong.
The variable 'i' gets increased to 3. And now you want to get a substring starting from the index 3 and ending with the index 6. The String "Cats" is only 4 letters, therefore the IndexOutOfBoundsException.
I guess the easiest way to solve your problem would be inserting a if else statement like this:
for(int i=0; i<s.length(); i=i+x){
if(s.length()>=i+x){
a=(a+s.substring(i,i+x)+"#");
}
else{
a= a+s.substring(i);
}
}

Related

Assistance with a java program that counts up to a number, in binary

I've recently taken up a computer organization course in where we learn binary hex etc, I took it upon myself to attempt to create a program that will count from 0 up to an input number, however the counting is done in binary. I've run into some trouble and confused myself beyond belief, some clarification and assistance would be greatly appreciated. Specifically speaking, how can I efficiently and effectively replace the values of a string containing the previous binary number, with 0's and 1's using some sort of for-loop. I'm aware that there is some method for directly converting a string to binary, however; I wanted to do this more complicated method for practice.
package counting;
import java.util.Scanner;
public class counting
{
public static void main(String[] args)
{
Scanner input = new Scanner(System.in);
System.out.println("Hello, this is a number counter, please enter the integer you would like to count to");
int number = input.nextInt();
String start = "0000000000";
// 000~etc is used as the start simply because i'm not sure how to calculate how many digit places
//the number input by the user will have
StringBuilder cont = new StringBuilder(start);
System.out.println(start);
/*What i intend to do is have the binary loop counter continue until it reaches
* the number input by the user, afterwards, working in a right to left manner, start counting from
* 0 up to the number given by the user, starting with 0. then using another loop, still using
* the right to left manner, if there is a 0, it should be replaced with a 1, and if there is a
* 1, it should be replaced with a 0, and the character before it should be replaced with a 1, if there
* is no room, continue to the left until there is a space available for a 1 and then reset all values
* after the 1 back to zero, and resume counting. the way i see it is requires a for loop to be used
* as the current position of a cursor used to determine what changes must be made
*/
for(int i = 0; i < number; i++)
{
int l = start.length();
for(int n = 0; n <= number; n++)
{
for(int w = 1; w <= l; w++)
{
if (cont.charAt(l-w) == '0')
{
cont.setCharAt((cont.length()-w), '1');
System.out.println(cont);
}
else if (cont.charAt(l-w) == '1')
{
cont.setCharAt((cont.length()-w), '0');
cont.setCharAt((cont.length()-(w+1)), '1');
System.out.println(cont);
}
}
}
System.out.println(cont);
}
}
}
Here is a little loop that will do what you are looking for. You just have to remember powers of 2 to count in binary.
public static char flip(char c){
if(c == '0')
return '1';
else
return '0';
}
public static void main(String[] args) {
String start = "0000000000";
StringBuilder cont = new StringBuilder(start);
int number = (int)Math.pow(2,10);
for(int i = 0; i < number; i++)
{
if(i != 0){
int val = (int)Math.floor(i/2);
for(int j = 0; j <= val; j++){
// Flip any bit that when modded by 2^j == 0
if(i % Math.pow(2,j) == 0){
cont.setCharAt((cont.length() - (j + 1)), flip(cont.charAt(cont.length() - (j + 1))));
}
}
}
System.out.println(cont);
}
}

Codingbat coverting recursive loop to for loop?

I am doing codingbat as practice for an upcoming quiz that I have. I am doing the recursion problems using recursion, but my teacher said that I should be able to do them using other loops. I figured that I should use for loops as they achieve are easily able to achieve the same result.
But I am having trouble converting the recursion to a for loop.
This is the problem:
Given a string and a non-empty substring sub, compute recursively the number of times that sub appears in the string, without the sub strings overlapping.
strCount("catcowcat", "cat") → 2
strCount("catcowcat", "cow") → 1
strCount("catcowcat", "dog") → 0
This is the code I am trying to use:
public int strCount(String str, String sub) {
int number = 0;
for (int i = 0; i >= str.length() - 1; i++) {
if (str.substring(i, sub.length()).equals(sub)) {
number += 1;
}
}
return number;
}
When I return, everything returns as 0.
In your for loop when you say
i >= str.length() - 1
the loop is never entered, because you are testing that i is greater than the allowed length (and it isn't). You need something like
i <= str.length() - 1
or
i < str.length()
Also, number += 1; can be written as number++;
One of the details you missed is "without the sub strings overlapping". This problem calls for a while loop, rather than a for loop, since the index will be incremented by different amounts, depending on whether there is a match or not.
Here's executable code to test whether or not the strCount method works correctly.
package com.ggl.testing;
public class StringCount {
public static void main(String[] args) {
StringCount stringCount = new StringCount();
System.out.println(stringCount.strCount("catcowcat", "cat"));
System.out.println(stringCount.strCount("catcowcat", "cow"));
System.out.println(stringCount.strCount("catcowcat", "dog"));
}
public int strCount(String str, String sub) {
int count = 0;
int length = str.length() - sub.length();
int index = 0;
while (index <= length) {
int substringLength = index + sub.length();
if (str.substring(index, substringLength).equals(sub)) {
count++;
index += sub.length();
} else {
index++;
}
}
return count;
}
}

So I was wondering why it truns out to be a false about my junit test

here is my solution
public int count_chars_in_String(String s, String s1){
int count = 0;
for(int j = 0; j<s1.length(); j++){
for(int i = 0; i<s.length();i++){
if(s.charAt(i) == s1.charAt(j)){
count += 1;
}
}
}
and here is my rest code
#Test public void tests4(){
code.Solution s = new code.Solution();
String input = "hhhhhey ";
String input1 = "hhh";
int expected = 3;
int actual = s.count_chars_in_String(input, input1);
assertTrue("Expected was" +expected+"but the actual was" +actual , expected == actual);
}
every time i run the junit test it shows up that Expected was3 but actual was 15? How???I am so confusing.
Code which would give you result 3 would look probably like (note the break statement):
// the outer loop
for(int j = 0; j<s1.length(); j++){
// the inner loop
for(int i = 0; i<s.length();i++){
if(s.charAt(i) == s1.charAt(j)){
count += 1;
// Break the inner loop after finding
// the match.
break;
}
}
}
Without the break, for each h in hhh (the outer loop), you increase the counter 5 times (the inner loop; because h occurs 5 times in hhhhhey).
do not know if this answer is what you are looking for and excuse my poor English.
The for j will run 3 times and for each of the times the for i will run 5 times, that are equal to the time that the condition is met. Now 5x3=15, the result that you get.
if what you expect is to get the number characters that match each string (3), then just do the following:
for(int i = 0; i<s1.length();i++){
if(s.charAt(i) == s1.charAt(i)){
count += 1;
}
}
Regards.

Nested loops/ASCII?

So, for an assignment in my computer science class, we've got to use loops, either for or while, depending on preference. Now, the assignment IS to use said loops and a given input to draw a beauteous ASCII diamond made of '$' and '-'. Say, an input of 5 would look like:
____$
___$-$
__$-$-$
_$-$-$-$
$-$-$-$-$
_$-$-$-$
__$-$-$
___$-$
____$
The underscores are to denote spaces. Now, anytime I try using
public static void main(String[] args) {
String input=JOptionPane.showInputDialog(null, "Input a number between three and ten here: ");
double length=Double.parseDouble(input);
int i=0; int j=0;
for(i=1; i<length; i++)
{
System.out.print(" ");
for(j=1; j<=i; j++)
{
if(j<i){System.out.print("-$");
}
else if(j==i){System.out.println("");}
}
}
I come out with something like, say, for input=7:
-$
-$-$
-$-$-$
-$-$-$-$
-$-$-$-$-$
And yes, the two too few in the center is true with any input. Any help?
Since this is your homework, I'm just going to point you towards the correct answer and leave you to figure out the rest. Let's try formatting your code so you can see what's going on:
public static void main(String[] args) {
String input=JOptionPane.showInputDialog(null, "Input a number between three and ten here: ");
double length=Double.parseDouble(input);
int i=0; int j=0;
for(i=1; i<length; i++){
System.out.print(" ");
for(j=1; j<=i; j++){
if(j<i){
System.out.print("-$");
}
else if(j==i){System.out.println("");
}
}
}
Now, you've got an outer loop for i ranging from 1..length-1, and for each i you're going to print a space, then you're going to count from 1 to 1 and print "-$" that many times. Then, you're going to print a newline and repeat the outer loop, incrementing i
So, the first time through the outer loop, you print one space, followed by one "-$", followed by a newline. Then on the second time through the outer loop, you print one space, followed by "-$" twice, followed by a newline. And so forth, until i=length, and then you stop.
You want to print a few more spaces before you print dollar signs - a loop here will probably be useful.
try to go trough this code and see how it works... it might be useful for your homework
public static void main(String[] args) {
Scanner input = new Scanner(System.in);
System.out.println("input a number");
int number = input.nextInt();
input.close();
boolean add = true;
int counter = 0;
do {
if (add) {
counter++;
print(' ', number - counter);
print('$', counter);
if (counter == number)
add = false;
System.out.println();
} else {
counter--;
if (counter == 0)
break;
print(' ', number - counter);
print('$', counter);
System.out.println();
}
} while (true);
}
private static void print(char c, int times) {
if (c == '$')
times = (times * 2) - 1;
for (int i = 0; i < times; i++)
System.out.print(c);
}
if you edit the print method you will get your desired result
private static void print(char c, int times) {
if (c == '$')
times = (times * 2) - 1;
for (int i = 0; i < times; i++)
if (i % 2 == 1 && c == '$')
System.out.print('-');
else
System.out.print(c);
}

Using for loop to get the Hamming distance between 2 strings

In this task i need to get the Hamming distance (the Hamming distance between two strings of equal length is the number of positions at which the corresponding symbols are different - from Wikipedia) between the two strings sequence1 and sequence2.
First i made 2 new strings which is the 2 original strings but both with lowered case to make comparing easier. Then i resorted to using the for loop and if to compare the 2 strings. For any differences in characters in these 2 pair of string, the loop would add 1 to an int x = 0. The returns of the method will be the value of this x.
public static int getHammingDistance(String sequence1, String sequence2) {
int a = 0;
String sequenceX = sequence1.toLowerCase();
String sequenceY = sequence2.toLowerCase();
for (int x = 0; x < sequenceX.length(); x++) {
for (int y = 0; y < sequenceY.length(); y++) {
if (sequenceX.charAt(x) == sequenceY.charAt(y)) {
a += 0;
} else if (sequenceX.charAt(x) != sequenceY.charAt(y)) {
a += 1;
}
}
}
return a;
}
So does the code looks good and functional enough? Anything i could to fix or to optimize the code? Thanks in advance. I'm a huge noob so pardon me if i asked anything silly
From my point the following implementation would be ok:
public static int getHammingDistance(String sequence1, String sequence2) {
char[] s1 = sequence1.toCharArray();
char[] s2 = sequence2.toCharArray();
int shorter = Math.min(s1.length, s2.length);
int longest = Math.max(s1.length, s2.length);
int result = 0;
for (int i=0; i<shorter; i++) {
if (s1[i] != s2[i]) result++;
}
result += longest - shorter;
return result;
}
uses array, what avoids the invocation of two method (charAt) for each single char that needs to be compared;
avoid exception when one string is longer than the other.
your code is completely off.
as you said yourself, the distance is the number of places where the strings differ - so you should only have 1 loop, going over both strings at once. instead you have 2 nested loops that compare every index in string a to every index in string b.
also, writing an if condition that results in a+=0 is a waste of time.
try this instead:
for (int x = 0; x < sequenceX.length(); x++) { //both are of the same length
if (sequenceX.charAt(x) != sequenceY.charAt(x)) {
a += 1;
}
}
also, this is still a naive approach which will probbaly not work with complex unicode characters (where 2 characters can be logically equal yet not have the same character code)
public static int getHammingDistance(String sequenceX, String sequenceY) {
int a = 0;
// String sequenceX = sequence1.toLowerCase();
//String sequenceY = sequence2.toLowerCase();
if (sequenceX.length() != sequenceY.length()) {
return -1; //input strings should be of equal length
}
for (int i = 0; i < sequenceX.length(); i++) {
if (sequenceX.charAt(i) != sequenceY.charAt(i)) {
a++;
}
}
return a;
}
Your code is OK, however I'd suggest you the following improvements.
do not use charAt() of string. Get char array from string using toCharArray() before loop and then work with this array. This is more readable and more effective.
The structure
if (sequenceX.charAt(x) == sequenceY.charAt(y)) {
a += 0;
} else if (sequenceX.charAt(x) != sequenceY.charAt(y)) {
a += 1;
}
looks redundant. Fix it to:
if (sequenceX.charAt(x) == sequenceY.charAt(y)) {
a += 0;
} else {
a += 1;
}
Moreover taking into account that I recommended you to work with array change it to something like:
a += seqx[x] == seqY[x] ? 0 : 1
less code less bugs...
EDIT: as mentionded by #radai you do not need if/else structure at all: adding 0 to a is redundant.

Categories