- There is. txt file of the following form:
3 2
12
12
2 4
4 2
13
12
2 1
Where are the first 4 digits: 3 is the number of matrices in the file (any number is not more than 130) 2 is the size of matrices (they are always square, any size is not more than 130) 1, 2 -i, j of the desired element of the resulting matrix All other numbers below are matrices themselves:
1 2 matrix 1
3 4
4 2 matrix 2
13
1 2 matrix 3
2 1
- Need to do. As a result, you need to output to the file the number from the resulting matrix with the coordinates for the row and column specified in the file (1, 2 in the given example). The resulting matrix is ​​the matrix obtained by multiplying the matrices from the file. In the above case, the answer is: 20
My code is:
import java.io.File; import java.io.FileNotFoundException; import java.io.PrintWriter; import java.util.ArrayList; import java.util.Arrays; import java.util.Scanner; /** * Created by Pazuk on 28.01.2018. */ // Main idea: // Step 1. Get all values from input file and according with it build array with numbers for matrices // Step 2. // Loop iteration: // - get numbers from array and create next matrix array // - multiply actual matrix with next matrix, get result matrix // - mark result matrix as actual matrix // Next iteration... // Step 3. After last iteration, get from result matrix requested number (positions specified in input file) public class Main { static int[] list; static boolean fileCheckOk=true; static int m; static int n; static int a; static int b; static int[][] matrixA; public static void main(String[] args) throws IOException { long startTime = System.currentTimeMillis(); long time = System.currentTimeMillis() - startTime; System.out.println(time); readFile(); time = System.currentTimeMillis()-startTime; System.out.println(time); if(fileCheckOk){ calculate(); PrintWriter writer=new PrintWriter("output.txt"); writer.print(matrixA[a-1][b-1]); writer.close(); } time = System.currentTimeMillis()-startTime; System.out.println(time); } static void readFile() throws IOException { StreamTokenizer tokenizer=new StreamTokenizer(new BufferedReader(new FileReader("input.txt"))); //general input values: tokenizer.nextToken(); m=(int)tokenizer.nval; // number of matricis tokenizer.nextToken(); n=(int)tokenizer.nval; // matrices size tokenizer.nextToken(); a=(int)tokenizer.nval; // position i of requested number tokenizer.nextToken(); b=(int)tokenizer.nval; // position j of requested number list=new int[m*n*n]; // array length according with quantity of matricis and their size int i=0; while(tokenizer.nextToken()!=StreamTokenizer.TT_EOF){ list[i]=(int)tokenizer.nval; i++; } /*if(m>=1 && m<=130 && n>=1 && n<=130 && a>=1 && a<=n && b>=1 && b<=n){ fileCheckOk=true; //check if input values are comply with task conditions }*/ } static void calculate(){ // calculate matrices int f, i, j, k; int r=0; int t; int temp; int[] thatColumn=new int[n]; int[] thisRow=new int[n]; int result=0; matrixA=new int[n][n]; // actual matrix for(f=0; f< m; f++){ // number of iterations==matrices quantity int[][] matrixB=new int[Main.n][Main.n]; // next matrix for(i=0; i< Main.n; i++){ for(j=0; j< Main.n; j++){ matrixB[i][j]=list[r]; r++; } } if(f>0){ int[][] matrixC=new int[Main.n][Main.n]; //result matrix for(j=0; j< Main.n; j++){ for(k=0; k< Main.n; k++){ thatColumn[k]=matrixB[k][j]; } for(i=0; i< Main.n; i++){ thisRow=matrixA[i]; result=0; for(k=0; k<Main.n; k++){ temp=thisRow[k]*thatColumn[k]; result=result+temp; } matrixC[i][j]=result; } } /*for(i=0; i< Main.n; i++){ for(j=0; j< Main.n; j++){ t=matrixA[i][k]; for(j=0; j< Main.n; j++){ temp=t*matrixB[k][j]; // multiplying... matrixC[i][j]=matrixC[i][j]+temp; // ...matrces } } }*/ matrixA=matrixC; } else { matrixA=matrixB; } } } } The code works and gives the correct answer. But does not pass tests because of too slow work. What could be the path of acceleration?
1 Maybe another internal matrix multiplication algorithm? Now they are multiplied "in the forehead":
for(int i=0; i<m; i++){ for(int j=0; j<n; j++){ for(int k=0; k<o; k++){ resultMatrix[i][j]+=mA[i][k]*mB[k][j]; } } } Well, almost like that. A little faster (see the calculate method).
2 Can be split calculations on separate threads?
3 Maybe another way to handle file data? Now each subsequent integer number of the file, the first 4 are assigned to variables, all others are driven into a one-dimensional array. From which we then take the values ​​to create matrices that are multiplied.
Something like this.
StreamTokenizerfrom acm.timus.ru/help.aspx?topic=java - zRrrBufferedReader(new StreamTokenizer(new BufferedReader(new FileReader(file)));) - zRrr