(牛客网)华为机试(二)

(牛客网)华为机试题集解答

在解题前先分享一波oj刷题的固定格式代码,方便输入时使用

import java.util.*;
import java.io.*;
public class Main{
    
       //一定要使用Main作为类名
    public static void main(String args[]){
    
    
        Scanner scanner = new Scanner(System.in);
        while(scanner.hasNext()){
    
    
            
        }
    }
}

如果是使用C++的话:

#include<bits/stdc++.h> //万能头文件,超级好用
using namespace std;
int main(){
    
    
    int num;
    while(scanf("%d",&num)!=EOF){
    
      //这里用cin也可以,个人喜好scanf(),因为一个有趣的手势(哈哈哈)       
    }
}

第五题 HJ104 字符串分割

题目要求在这里插入图片描述在这里插入图片描述在这里插入图片描述

思路:

直接对输入的数据进行一次判断:输入的字符串长度是否是8的倍数,如果是8的倍数就不管,如果不是就直接在字符串后面补上缺少的零的个数强迫它变成8的倍数,然后使用substring函数进行截取字符串,每8个输出一行即可。如果是使用python解答的化就更简单,因为可以进行切片操作。

import java.util.Scanner;
public class Main{
    
    
    public static void main(String args[]){
    
    
        Scanner scanner = new Scanner(System.in);
        while(scanner.hasNext()){
    
    
            int n=scanner.nextInt();
            for(int i=0;i<n;i++){
    
    
                String words = scanner.next();
                while(words.length()%8!=0){
    
    
                    words +="0";
                }
                for(int j=0;j<words.length();j+=8){
    
    
                    System.out.println(words.substring(j,j+8));
                }
            }
        }
    }
}

如果是python的化就这样即可(python非本人写)

while True:
    try:
        a= int(input())
        for i in range(a):
            s=input()
            while len(s)>8:
                print(s[:8])
                s=s[8:]
            print(s.ljust(8,"0"))
    except:
        break

第六题:HJ103 Redraiment的走法

题目要求

在这里插入图片描述在这里插入图片描述

思路:

开始看到这道题目一脸懵逼,都没读懂题意啥意思,然后仔细看一遍发现其本质就是早最长上升子序列。所以这道题目就变得简单了起来,在没有学过动态规划之前,做起来肯定就是想直接暴力解决了,但这类题目基本上暴力都会超时,所以我们要学会使用空间换时间。先开一个数组来记录一部分数据,边找变记录。使用这个数组来记录每一个数字当前位置所能出现的最长递增子序列长度,使用迭代的思路来求解长度,具体的其动态规划的思路如下:
例如:给定一个长度为6的数组A{6, 2, 5, 1,4, 5},则其最长的单调递增子序列为{1,4,5}或者{2,4,5},长度为3。
记d[i]为以任意一个A[i]为末尾元素组成的最长递增子序列的长度,找出所有位于i之前且比A[i]小的元素A[j],此时可出现两种情况:
(1)若找到,例如i = 2,此时A[i] = 5,比A[i]小的元素为A[1] = 2,取所有比A[i]小的元素中A[j]中,对应的d[j]最大的加1,即d[i] = max{ d[j] },其中j < i 且 A[j] < A[i];
(2)若没有找到,例如i = 3,此时A[3] = 1,i之前不存在比1小的元素,此时A[3] = 1独自构成一个递增子序列,d[i] = 1。
当i = 0时,此时A[0] = 6,只有一个元素独自构成子序列,此时d[0] = 1;
当i = 1时,此时A[1] = 2,i = 3之前不存在比1小的元素,即d[1] = d[0] =1;
当i = 2时,此时A[2] = 5,比A[2]小的元素分别为 A[1] = 2,取对应的d[j]最大的d[1] = 1,即i = 2时对应最长递增子序列长度应为d[2] = d[1] + 1 = 2;
当i = 3时,此时A[3] = 1,i = 3 之前不存在比1小的元素, 即d[3] = 1;
当i = 4时,此时A[4] = 4,比A[4]小的元素为2和1,有两个元素,取对应的d[j]最大的d[1]=d[3]=1,即i = 2时对应最长递增子序列长度应为d[4] = d[1] + 1 = 2;
当i = 5时,此时A[5] = 5,前5个元素有1,2,4,,取对应最大的d[j]为当j = 4时,此时d[4] = 2,即i = 5时对应的最长的递增子序列长度为d[5] = d[4] + 1 = 3。
最后再遍历所开的数组,找出最大的数字即为最长递增子序列,听起来是不是很简单呢?为方便写代码我们利用java自带的Math.max()函数提高效率。

import java.util.*;
public class Main{
    
    
    public static void main(String[] args){
    
    
        Scanner scanner = new Scanner(System.in);
        while(scanner.hasNextInt()){
    
    
            int count = scanner.nextInt();
            int[] A = new int[count];
            for(int i=0;i<count;i++){
    
    
                A[i]= scanner.nextInt();
            }
              
            System.out.println(good(count, A));  //dp函数部分
        }
    }
        public static int good(int a,int[] b){
    
    
        int[] dp = new int[a];
        int max=1;
        for(int i=0;i<a;i++){
    
    
            dp[i]=1;
            for(int j=0;j<i;j++){
    
    
                if(b[j]<b[i]){
    
    
                dp[i]=Math.max(dp[i],dp[j]+1);
                }
            }
            max=Math.max(dp[i],max);
        }
        return max;
    }
}

由于最近家里这边暴雨原因,经常性的发生停电,所以今天就刷了两题,争取每天两题到四题,检查就是胜利,刚开始学着刷刷上机题,大家一起努力!!!!

good good studym,day day up! (study hard, improve every day)

预知后事,请听下回分解!!!!

下一篇地址:(牛客网)华为机试(三)

猜你喜欢

转载自blog.csdn.net/qq_41606378/article/details/107328047