旋转数组的程序;是否抛出了超过时限(TLE)?如何使用BufferedReader优化和进一步修复?

时间:2019-06-15 09:55:40

标签: java arrays

给出大小为N的未排序数组arr [],将其旋转D个元素(顺时针)。

输入:

输入的第一行包含T,表示测试用例的数量。每个测试用例的第一行包含两个以空格分隔的元素,N表示数组的大小,而整数D表示转数的大小。接下来的行将是N个以空格分隔的数组元素。

输出:

对于每个测试用例,在新行中输出旋转后的数组。

约束:

1 <= T <= 200
1 <= N <= 107
1 <= D <= N
0 <= arr[i] <= 105

示例: 输入:

2
5 2
1 2 3 4 5 
10 3
2 4 6 8 10 12 14 16 18 20

输出:

3 4 5 1 2
8 10 12 14 16 18 20 2 4 6

说明:

Testcase 1: 1 2 3 4 5  when rotated by 2 elements, it becomes 3 4 5 1 2.

我已经使用Scanner类进行了相同的编码,但是它抛出了超过时间限制。

1. I need a better solution.
2. I read here that BufferedReader helps avoid TLE
3. I tried using it; but when i take input it throws NumberFormatException.

这是我的代码:(使用扫描仪类)

import java.util.*;
import java.lang.*;
import java.io.*;

class rotat {
    public static void main (String[] args) {
 Scanner sc= new Scanner(System.in);
 int t= sc.nextInt();
 while(t-->0){
     int s= sc.nextInt();
     int arr[]= new int[s];
     for(int i=0;i<s;i++){
         arr[i]=sc.nextInt();
     }
     int k= sc.nextInt();
     while(k-->0){
     int temp=arr[0];
     for(int j=1; j<s;j++){
        arr[j-1]=arr[j]; 
 }
 arr[s-1]=temp;
     }
 for(int j=0; j<s;j++){
        System.out.print(arr[j]+" ");
 }
 System.out.println();

    }
}}

对于自定义测试用例,它运行良好。

这是我使用Buffered Input的代码:(这是我的新手;我一直使用Scanner类,因此我的代码可能是完全错误的。)

import java.util.*;
import java.lang.*;
import java.io.*;

class rotat {
    public static void main (String[] args)throws IOException {
  BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); 

        int t =Integer.parseInt(br.readLine());
        System.out.println(t); 
 while(t-->0){
     int s= Integer.parseInt(br.readLine());
     System.out.println(s);
     int k= Integer.parseInt(br.readLine());
     System.out.println(k);
     int arr[]= new int[s];
     for(int i=0;i<s;i++){
         arr[i]=Integer.parseInt(br.readLine());
     }

     while(k-->0){
     int temp=arr[0];
     for(int j=1; j<s;j++){
        arr[j-1]=arr[j]; 
 }
 arr[s-1]=temp;
     }
 for(int j=0; j<s;j++){
        System.out.print(arr[j]+" ");
 }
 System.out.println();

    }
}}

运行时错误:

Runtime ErrorException in thread "main" java.lang.NumberFormatException: For input string: "5 2" at java.lang.NumberFormatException.forInputString(NumberFormatException.java:65)
    at java.lang.Integer.parseInt(Integer.java:580)
    at java.lang.Integer.parseInt(Integer.java:615)
    at GFG.main(File.java:13)

4 个答案:

答案 0 :(得分:2)

解决方案

import java.util.*;
import java.lang.*;
import java.io.*;

    class Main { 
        /*here we define funtion to left rotate arr[] of size n by d is number of rotation*/
        void leftRotate(int arr[], int d, int n) 
        { 
            for (int i = 0; i < d; i++) 
                leftRotatebyOne(arr, n); 
        } 
      
        void leftRotatebyOne(int arr[], int n) 
        { 
            int i, temp; 
            temp = arr[0]; 
            for (i = 0; i < n - 1; i++) 
                arr[i] = arr[i + 1]; 
            arr[i] = temp; 
        } 
      
        /* utility function to print an array */
        void printArray(int arr[], int n) 
        { 
            for (int i = 0; i < n; i++) {
                System.out.print(arr[i] + " "); 
            }
    
          System.out.println();
        } 
      
        // This main method we test above functions 
        public static void main(String[] args) 
        { 
            int n,d;;
            //Main=RotationClass
            
        Scanner sc=new Scanner(System.in);  
    
    //t define the number of testcases    
    int t = sc.nextInt();
            
        for(int k=0;k<t;k++){
           
            n=sc.nextInt();
            d=sc.nextInt();
    
            int[] array = new int[n]; 
            for(int i=0;i<n;i++){
                array[i]=sc.nextInt();
            }
            
            Main rotate = new Main(); 
            rotate.leftRotate(array, d, n); 
            rotate.printArray(array,n); 
            
        } 
       }
    } 

答案 1 :(得分:1)

我想知道为什么使用Scanner旋转数组?要旋转数组(向左或向右),可以使用以下技巧。

ABCDEFG -> FGABCDE

1. GFEDCBA -> rotate A...G
2. FGEDCBA -> rotate G...F
3. FGABCDE -> rotate E...A

代码

private static void leftRotate(int[] a, int k) {
    k = k >= a.length ? a.length % k : k;

    for (int i = 0, j = a.length - 1; i < j; i++, j--)
        swap(a, i, j);
    for (int i = 0, j = a.length - k - 1; i < j; i++, j--)
        swap(a, i, j);
    for (int i = a.length - k, j = a.length - 1; i < j; i++, j--)
        swap(a, i, j);
}

private static void swap(int[] a, int i, int j) {
    int tmp = a[i];
    a[i] = a[j];
    a[j] = tmp;
}

答案 2 :(得分:0)

I have a solution for c++, not totally implemented!
    int test_case ;
    int n = 10 ;
    int rotate_array = 3 ;
    int arr[] = {2, 4 ,6 ,8, 10, 12, 14, 16, 18, 20};
    for (int i = 0 ; i <= n ; i ++ ){
        if(i <= rotate_array) {
            arr[n + i] = arr[i];
        }
    }
    for (int i = 0 ; i < n ; i ++ ){
        arr[i] = arr[rotate_array + i];
    }

答案 3 :(得分:-1)

BufferedReader将整行作为输入,当您将其输入为“ 5 2”时,它将尝试将其解析为整数。现在有问题了。我建议将StringTokenizer和BufferedReader一起使用来克服这个问题。

while(t-->0){
   StringTokenizer st = new StringTokenizer(br.readLine());
   int s = Integer.parseInt(st.nextToken());
   int k = Integer.parseInt(st.nextToken());
   // to take new line in input
   StringTokenizer arrInput = new StringTokenizer(br.readLine());
   int[] arr = new int[s];
   for(int i=0;i<s;i++){
       arr[i] = Integer.parseInt(arrInput.nextToken());
   }
   int[] answer = new int[s];

   for(int j=0; j<s;j++){
       answer[(j-k+s)%s]=arr[j];
   }
   for(int j=0;j<s;j++){
       arr[j] = answer[j];
   }
}
//all you need to do is print your arr array.

只要一行中有多个值,就可以使用StringTokenizer。它通过在空格处断开字符串并形成一组字符串来创建该字符串的令牌,可以使用该StringTokenizer对其进行访问。