unsigned multiplication & sum algorithm - java

I'm trying to make an algorithm in java that makes an unsigned multiplication. This algorithm, then, make use of an unsigned sum. This is the code:
public int[] unsignedSum(int[] n1, int[] n2){
int[] result = new int[48];
int carry = 0;
for(int x = 47; x >= 0; x--){
if (n1[x]+n2[x]+carry == 1){
result[x] = 1;
carry = 0;
}
else if (n1[x]+n2[x]+carry == 2)
carry = 1;
else if (n1[x]+n2[x]+carry == 3)
result[x] = 1;
}
return result;
}
public int[] unsignedMult(int[] n1, int[] n2){
int[] result = new int[48];
int[] N1 = new int[48];
int[] N2 = new int[48];
//fix the size to 48
for (int x = 24; x < 48; x++){
N1[x] = n1[x-24];
N2[x] = n2[x-24];
}
for(int x = 47; x >= 0; x--){
if (N2[x] == 1){
int[] shiftedN1 = new int[48];
for (int y = 0; y < x; y++)
shiftedN1[y] = N1[y+48-x];
result = unsignedSum(result, shiftedN1);
}
}
return result;
}
Vectors n1 and n2 have size 24
any other vector have size 48
the problem is: it's eating the first number in some cases.
the multiplication should never overflow, but in this case, it does somehow.
1100000...(24bits) * 1100000(24bits).. should result in 10010000...(48 bits), but it's resulting in 00100000...(48 bits)

Look for 2 off-by-one errors in
for (int y = 0; y < x; y++)
shiftedN1[y] = N1[y+48-x];
What is exactly the off-by-one errors in the while loop?
You may want to run the above loop by hand with simple case of ....0001 * ....0001

Related

Calculate factorial of 50 using array only in java

I'm a total beginner of java.
I have a homework to write a complete program that calculates the factorial of 50 using array.
I can't use any method like biginteger.
I can only use array because my professor wants us to understand the logic behind, I guess...
However, he didn't really teach us the detail of array, so I'm really confused here.
Basically, I'm trying to divide the big number and put it into array slot. So if the first array gets 235, I can divide it and extract the number and put it into one array slot. Then, put the remain next array slot. And repeat the process until I get the result (which is factorial of 50, and it's a huge number..)
I tried to understand what's the logic behind, but I really can't figure it out.. So far I have this on my mind.
import java.util.Scanner;
class Factorial
{
public static void main(String[] args)
{
int n;
Scanner kb = new Scanner(System.in);
System.out.println("Enter n");
n = kb.nextInt();
System.out.println(n +"! = " + fact(n));
}
public static int fact(int n)
{
int product = 1;
int[] a = new int[100];
a[0] = 1;
for (int j = 2; j < a.length; j++)
{
for(; n >= 1; n--)
{
product = product * n;
a[j-1] = n;
a[j] = a[j]/10;
a[j+1] = a[j]%10;
}
}
return product;
}
}
But it doesn't show me the factorial of 50.
it shows me 0 as the result, so apparently, it's not working.
I'm trying to use one method (fact()), but I'm not sure that's the right way to do.
My professor mentioned about using operator / and % to assign the number to the next slot of array repeatedly.
So I'm trying to use that for this homework.
Does anyone have an idea for this homework?
Please help me!
And sorry for the confusing instruction... I'm confused also, so please forgive me.
FYI: factorial of 50 is 30414093201713378043612608166064768844377641568960512000000000000
Try this.
static int[] fact(int n) {
int[] r = new int[100];
r[0] = 1;
for (int i = 1; i <= n; ++i) {
int carry = 0;
for (int j = 0; j < r.length; ++j) {
int x = r[j] * i + carry;
r[j] = x % 10;
carry = x / 10;
}
}
return r;
}
and
int[] result = fact(50);
int i = result.length - 1;
while (i > 0 && result[i] == 0)
--i;
while (i >= 0)
System.out.print(result[i--]);
System.out.println();
// -> 30414093201713378043612608166064768844377641568960512000000000000
Her's my result:
50 factorial - 30414093201713378043612608166064768844377641568960512000000000000
And here's the code. I hard coded an array of 100 digits. When printing, I skip the leading zeroes.
public class FactorialArray {
public static void main(String[] args) {
int n = 50;
System.out.print(n + " factorial - ");
int[] result = factorial(n);
boolean firstDigit = false;
for (int digit : result) {
if (digit > 0) {
firstDigit = true;
}
if (firstDigit) {
System.out.print(digit);
}
}
System.out.println();
}
private static int[] factorial(int n) {
int[] r = new int[100];
r[r.length - 1] = 1;
for (int i = 1; i <= n; i++) {
int carry = 0;
for (int j = r.length - 1; j >= 0; j--) {
int x = r[j] * i + carry;
r[j] = x % 10;
carry = x / 10;
}
}
return r;
}
}
How about:
public static BigInteger p(int numOfAllPerson) {
if (numOfAllPerson < 0) {
throw new IllegalArgumentException();
}
if (numOfAllPerson == 0) {
return BigInteger.ONE;
}
BigInteger retBigInt = BigInteger.ONE;
for (; numOfAllPerson > 0; numOfAllPerson--) {
retBigInt = retBigInt.multiply(BigInteger.valueOf(numOfAllPerson));
}
return retBigInt;
}
Please recall basic level of math how multiplication works?
2344
X 34
= (2344*4)*10^0 + (2344*3)*10^1 = ans
2344
X334
= (2344*4)*10^0 + (2344*3)*10^1 + (2344*3)*10^2= ans
So for m digits X n digits you need n list of string array.
Each time you multiply each digits with m. and store it.
After each step you will append 0,1,2,n-1 trailing zero(s) to that string.
Finally, sum all of n listed string. You know how to do that.
So up to this you know m*n
now it is very easy to compute 1*..........*49*50.
how about:
int[] arrayOfFifty = new int[50];
//populate the array with 1 to 50
for(int i = 1; i < 51; i++){
arrayOfFifty[i-1] = i;
}
//perform the factorial
long result = 1;
for(int i = 0; i < arrayOfFifty.length; i++){
result = arrayOfFifty[i] * result;
}
Did not test this. No idea how big the number is and if it would cause error due to the size of the number.
Updated. arrays use ".length" to measure the size.
I now updated result to long data type and it returns the following - which is obviously incorrect. This is a massive number and I'm not sure what your professor is trying to get at.
-3258495067890909184

Java: Square Matrix Multiplication by means of recursion

I need to write a recursive method that multiplies 2 square matrices (size n-by-n).
It needs to run in theta(N^3) time but it's not Strassen's algorithm.
I've written a method but I am getting a stack overflow.
Matrix A is Matrix B is
1 2 1 0 3 2 3 0
2 3 2 0 2 1 2 0
1 2 1 0 3 2 3 0
The two matrices are both int[][]. here is the code I have written:
public int[][] ncubed(int [][]A, int [][]B){
int w = A.length;
int [][] C = new int[w][w];
if (w==1){
C[0][0] = A[0][0] * B[0][0];
}
else{
int [][]A1 = partition(1,A);
int [][]A2 = partition(2,A);
int [][]A3 = partition(3,A);
int [][]A4 = partition(4,A);
int [][]B1 = partition(1,B);
int [][]B2 = partition(2,B);
int [][]B3 = partition(3,B);
int [][]B4 = partition(4,B);
int [][]C1 = partition(1,C);
int [][]C2 = partition(2,C);
int [][]C3 = partition(3,C);
int [][]C4 = partition(4,C);
C1 = add(ncubed(A1,B1),ncubed(A2,B3));
C2 = add(ncubed(A1,B2),ncubed(A2,B4));
C3 = add(ncubed(A3,B1),ncubed(A4,B3));
C4 = add(ncubed(A3,B2),ncubed(A4,B4));
join(C1, C, 0 , 0);
join(C2, C, w/2 , 0);
join(C3, C, 0, w/2);
join(C4, C, w/2, w/2);
}
return C;
}
public int [][] partition(int quadrant, int[][] array){
int n = array.length;
int[][] Q = new int[array.length][array.length];
if(quadrant>4 || quadrant<1) return null;
switch(quadrant){
case(1):
for(int i = 0; i<(n/2); i++){
for(int j = 0; j<(n/2); j++){
Q[i][j] = array[i][j];
}
}
break;
case(2):
for(int i = n/2; i<n; i++){
for(int j = 0; j<(n/2); j++){
Q[i][j] = array[i][j];
}
}
break;
case(3):
for(int i = 0; i<(n/2); i++){
for(int j = (n/2); j<n; j++){
Q[i][j] = array[i][j];
}
}
break;
case(4):
for(int i = (n/2); i<n; i++){
for(int j = (n/2); j<n; j++){
Q[i][j] = array[i][j];
}
}
break;
}
return Q;
}
The methods add and join work fine because I've tested them so it's not in that part.
I just can't figure out my problem in the actual ncubed method(the matrix multiply method).
If anyone is able to help me understand something I'm doing incorrectly or show me another way to do this with the specifications stated at the top, that would be awesome. Thanks for any help.
The naive method will give you theta(n^3) time -- have you checked out something simpler?
Failing that, have you looked at these similar questions?

2D Array to Rectangles

Is there a way to parse 2 dimensional array like this into a rectangle object (x,y, width, height)?. I need the array of all possible rectangles...
{0,0,0,0,0}
{0,0,0,0,0}
{0,1,1,0,0}
{0,1,1,0,0}
{0,0,0,0,0}
This would give 4 rectangles (we are looking at 0):
0,0,5,2
0,0,1,5
3,0,2,5
0,5,5,1
I have tried something like this, but it only gives the area of the biggest rectangle...
public static int[] findMaxRectangleArea(int[][] A, int m, int n) {
// m=rows & n=cols according to question
int corX =0, corY = 0;
int[] single = new int[n];
int largeX = 0, largest = 0;
for (int i = 0; i < m; i++) {
single = new int[n]; // one d array used to check line by line &
// it's size will be n
for (int k = i; k < m; k++) { // this is used for to run until i
// contains element
int a = 0;
int y = k - i + 1; // is used for row and col of the comming
// array
int shrt = 0, ii = 0, small = 0;
int mix = 0;
int findX = 0;
for (int j = 0; j < n; j++) {
single[j] = single[j] + A[k][j]; // postions element are
// added
if (single[j] == y) { // element position equals
shrt = (a == 0) ? j : shrt; // shortcut
a = a + 1;
if (a > findX) {
findX = a;
mix = shrt;
}
} else {
a = 0;
}
}
a = findX;
a = (a == y) ? a - 1 : a;
if (a * y > largeX * largest) { // here i am checking the values
// with xy
largeX = a;
largest = y;
ii = i;
small = mix;
}
}
}// end of loop
return largeX * largest;
}
this code is working with 1s, but that is not the point right now

How to times all the values together in an array list

I would like to multiply each value inside an arraylist of integers. For example,
I have an array list which contains the following numbers:
5, 5, 5, 5
How would I create an integer that contains all these numbers multiplied by eachother:
int x = 5 * 5 * 5 * 5
In my case I'm returning it with a method, like so:
List<Integer> stack = new ArrayList<Integer>();
public int multiply() {
int x = 0;
for (int i = 0; i < stack.size(); i++) {
x *= stack.get(i);
}
return x;
}
List<Integer> stack = new ArrayList<Integer>();
public int multiply() {
int x = 0;
for (int i = 0; i < stack.size(); i++) {
x *= stack.get(i);
}
return x;
}
Think about, what ONE time 0* means to the final number..? Got it? Fix it!
Simply loop through your ArrayList and multiply away:
int foo=1;
for(int i : list) {
foo *= i;
}
You have a problem here
public int multiply() {
int x = 0;
for (int i = 0; i < stack.size(); i++) {
x *= stack.get(i);
}
return x;
}
since you initialise x with zero - multiply it by anything and its still zero.
Change this line to
int x = 1;
and you should be good
Umm you should initialize your result (x) to 1! (zero times anything is zero)
int number1 = 1;
for (int i = 0; i < list.size(); i++) {
number1 *= list.get(i);
}
System.out.println(number1);
I made 'number1' equal 1 because any number times 1 is the number. after the loop 'number1' is printed. Complete syntax of 'number1 *= list.get(i);' ->
number1 = number1 * list.get(i);

Port Matlab's FFT to native Java

I want to port Matlab's Fast Fourier transform function fft() to native Java code.
As a starting point I am using the code of JMathLib where the FFT is implemented as follows:
// given double[] x as the input signal
n = x.length; // assume n is a power of 2
nu = (int)(Math.log(n)/Math.log(2));
int n2 = n/2;
int nu1 = nu - 1;
double[] xre = new double[n];
double[] xim = new double[n];
double[] mag = new double[n2];
double tr, ti, p, arg, c, s;
for (int i = 0; i < n; i++) {
xre[i] = x[i];
xim[i] = 0.0;
}
int k = 0;
for (int l = 1; l <= nu; l++) {
while (k < n) {
for (int i = 1; i <= n2; i++) {
p = bitrev (k >> nu1);
arg = 2 * (double) Math.PI * p / n;
c = (double) Math.cos (arg);
s = (double) Math.sin (arg);
tr = xre[k+n2]*c + xim[k+n2]*s;
ti = xim[k+n2]*c - xre[k+n2]*s;
xre[k+n2] = xre[k] - tr;
xim[k+n2] = xim[k] - ti;
xre[k] += tr;
xim[k] += ti;
k++;
}
k += n2;
}
k = 0;
nu1--;
n2 = n2/2;
}
k = 0;
int r;
while (k < n) {
r = bitrev (k);
if (r > k) {
tr = xre[k];
ti = xim[k];
xre[k] = xre[r];
xim[k] = xim[r];
xre[r] = tr;
xim[r] = ti;
}
k++;
}
// The result
// -> real part stored in xre
// -> imaginary part stored in xim
Unfortunately it doesn't give me the right results when I unit test it, for example with the array
double[] x = { 1.0d, 5.0d, 9.0d, 13.0d };
the result in Matlab:
28.0
-8.0 - 8.0i
-8.0
-8.0 + 8.0i
the result in my implementation:
28.0
-8.0 + 8.0i
-8.0
-8.0 - 8.0i
Note how the signs are wrong in the complex part.
When I use longer, more complex signals the differences between the implementations affects also the numbers. So the implementation differences does not only relate to some sign-"error".
My question: how can I adapt my implemenation to make it "equal" to the Matlab one?
Or: is there already a library that does exactly this?
in order to use Jtransforms for FFT on matrix you need to do fft col by col and then join them into a matrix. here is my code which i compared with Matlab fft
double [][] newRes = new double[samplesPerWindow*2][Matrixres.numberOfSegments];
double [] colForFFT = new double [samplesPerWindow*2];
DoubleFFT_1D fft = new DoubleFFT_1D(samplesPerWindow);
for(int y = 0; y < Matrixres.numberOfSegments; y++)
{
//copy the original col into a col and and a col of zeros before FFT
for(int x = 0; x < samplesPerWindow; x++)
{
colForFFT[x] = Matrixres.res[x][y];
}
//fft on each col of the matrix
fft.realForwardFull(colForFFT); //Y=fft(y,nfft);
//copy the output of col*2 size into a new matrix
for(int x = 0; x < samplesPerWindow*2; x++)
{
newRes[x][y] = colForFFT[x];
}
}
hope this what you are looking for. note that Jtransforms represent Complex numbers as
array[2*k] = Re[k], array[2*k+1] = Im[k]

Categories