华为机试简单题
1.字符串最后一个单词的长度
描述
计算字符串最后一个单词的长度,单词以空格隔开,字符串长度小于5000。(注:字符串末尾不以空格为结尾)
输入描述:
输入一行,代表要计算的字符串,非空,长度小于5000。
输出描述:
输出一个整数,表示输入字符串最后一个单词的长度。
示例1
输入:
hello nowcoder
输出:
8
说明:
最后一个单词为nowcoder,长度为8
import java.util.*;
public class Main{
public static void main(String[] args) throws Exception{
Scanner sc=new Scanner(System.in);
String str=sc.nextLine();
String[] strs=str.split(" ");
int length=strs[strs.length-1].length();
System.out.println(length);
}
}
2.计算某一个字符出现的次数
描述
写出一个程序,接受一个由字母、数字和空格组成的字符串,和一个字符,然后输出输入字符串中该字符的出现次数。(不区分大小写字母)
数据范围: 1 \le n \le 1000 \1≤n≤1000
输入描述:
第一行输入一个由字母和数字以及空格组成的字符串,第二行输入一个字符。
输出描述:
输出输入字符串中含有该字符的个数。(不区分大小写字母)
示例1
输入:
ABCabc
A
输出:
2
写法一:
import java.util.*;
public class Main{
public static void main(String args[]){
Scanner sc=new Scanner(System.in);
String s1=sc.nextLine().toUpperCase();//因为不区分大小写都要进行比对,所以都转成大写来判断
String s2=sc.nextLine().toUpperCase();
String[] str=s1.split("");
int count=0;
for(int i=0;i<str.length;i++){
if(str[i].equals(s2))
count++;
}
System.out.println(count);
}
}
写法二:
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String str = sc.nextLine().toUpperCase();
char c = sc.next().toUpperCase().charAt(0);//因为第二行输入仅为一个A,所以通过charAt(0)直接获取输入字符串的第一个字符即可,并且要转为大写。
int num = 0;
//注意要把str转为char数组后,再用s遍历,然后进行对比
for(char s: str.toCharArray()) {
if(c==s) {
num +=1;
}
}
System.out.println(num);
}
}
3.字符串分割
描述
•输入一个字符串,请按长度为8拆分每个输入字符串并进行输出;
•长度不是8整数倍的字符串请在后面补数字0,空字符串不处理。
输入描述:
连续输入字符串(每个字符串长度小于等于100)
输出描述:
依次输出所有分割后的长度为8的新字符串
示例1
输入:
abc
输出:
abc00000
写法一,直接把整个一行输入的字符串获取,按位数添加0之后再每8位分开输出
import java.util.*;
public class Main{
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
while(sc.hasNext()){
String str = sc.nextLine();
StringBuilder sb = new StringBuilder();//牢记字符串缓冲区的建立语法
sb.append(str);//字符串缓冲区的加入
int size = str.length();
int addZero = 8 - size%8;//addzero的可能值包括8
while((addZero > 0)&&(addZero<8)){//注意边界调节,避免addzero=8
sb.append("0");//使用‘’或“”都可
addZero--;
}
String str1 = sb.toString();
while(str1.length()>0){
System.out.println(str1.substring(0,8));
str1 = str1.substring(8);
}
}
}
}
写法二,先每8位每8位地取,直到不足八位的最后一组,添加8个零之后,取1~8位
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String str;
while (sc.hasNext()) {
str = sc.nextLine();
while (str.length() > 8) {
System.out.println(str.substring(0, 8));
str = str.substring(8);
}
str = str + "00000000";
System.out.println(str.substring(0, 8));
}
}
}
注:hasNext()为判断是否有输入
nextLine();只以回车作为结束符取值
next();以回车 空格 tab 为结束符取值
substring(i,e) 取到该字符串从i~e位,
substring(i) 去除前i位取后面的所有位
4.进制转换
描述
写出一个程序,接受一个十六进制的数,输出该数值的十进制表示。
数据范围:保证结果在 1 \le n \le 2^{31}-1 \1≤n≤231−1
输入描述:
输入一个十六进制的数值字符串。
输出描述:
输出该数值的十进制字符串。不同组的测试用例用\n隔开。
示例1
输入:
0xAA
输出:
170
import java.io.*;
import java.util.*;
public class Main{
public static void main(String[] args) throws Exception{
Scanner sc = new Scanner(System.in);
while(sc.hasNextLine()){
String s = sc.nextLine();
System.out.println(Integer.parseInt(s.substring(2,s.length()),16));
}
}
}
substring(int a,int b)方法可以截断字符串,当只有一个参数时,截取范围是[a,length-1],当有两个参数时,截取范围是[a,b-1]。
Integer.parseInt(String s,int a)方法可以转换进制,将字符串转换为“a”进制,只有一个参数s时,转换为10进制。 parseInt本身为将传入参数转化为10进制输出
5.质数因子
描述
功能:输入一个正整数,按照从小到大的顺序输出它的所有质因子(重复的也要列举)(如180的质因子为2 2 3 3 5 )
数据范围: 1 \le n \le 2 \times 10^{9} + 14 \1≤n≤2×109+14
输入描述:
输入一个整数
输出描述:
按照从小到大的顺序输出它的所有质数的因子,以空格隔开。
示例1
输入:
180
输出:
2 2 3 3 5
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
long num = scanner.nextLong();
long k = (long) Math.sqrt(num);//取输入数值的根植
for (long i = 2; i <= k; i++) {
while (num % i == 0) {//从2开始一直取模为0则打印记录,直到2不满足条件,i++,因为题中要求包括相同的质数因子也需要打印
System.out.print(i + " ");
num /= i;//每一次判断完num%i之后要把这个分子除掉并且赋值给num。
}
}
System.out.println(num == 1 ? "": num+" ");//如果num为1那么说明num本身不是质数,反之是质数。
}
}
//牛客网大佬所言:此题,如果代码的最坏时间复杂度是线性的,只能通过大概 91% 的样例(我使用 java 的测试结果),原因之所在就是会有超大素数作为特殊样例来恶心人;但是正如我们判断数 num 是不是质数时,没必要从 2 一直尝试到 num 一样,此题中的大循环也大可不必写一个到 num 的循环,写到更号num即可,如果此时数字还没有除数,则可判定其本身是一个质数,没有再除下去的必要了,直接打印其本身即可
6.取近似值
描述
写出一个程序,接受一个正浮点数值,输出该数值的近似整数值。如果小数点后数值大于等于 0.5 ,向上取整;小于 0.5 ,则向下取整。
数据范围:保证输入的数字在 32 位浮点数范围内
输入描述:
输入一个正浮点数值
输出描述:
输出该数值的近似整数值
示例1
输入:
5.5
输出:
6
说明:
0.5>=0.5,所以5.5需要向上取整为6
示例2
输入:
2.499
输出:
2
说明:
0.499<0.5,2.499向下取整为2
import java.util.Scanner;
public class Main{
public static void main(String args[]){
Scanner sc=new Scanner(System.in);
double number=sc.nextDouble();
System.out.println((int)(number+0.5));//利用类型强制转换,当double转为int的时候会直接舍去小数位的精度,所以直接给当前double值加上0.5再转换即可满足题中条件。
}
}
7.合并表记录
描述
数据表记录包含表索引index和数值value(int范围的正整数),请对表索引相同的记录进行合并,即将相同索引的数值进行求和运算,输出按照index值升序进行输出。
提示:
0 <= index <= 11111111
1 <= value <= 100000
输入描述:
先输入键值对的个数n(1 <= n <= 500)
接下来n行每行输入成对的index和value值,以空格隔开
输出描述:
输出合并后的键值对(多行)
示例1
输入:
4
0 1
0 2
1 2
3 4
输出:
0 3
1 2
3 4
示例2
输入:
3
0 1
0 2
8 9
输出:
0 3
8 9
方法一,采用hashMap,其缺点是不支持map中的自动排序,但是hashmap在遍历的时候是按照键的大小进行一个遍历输出的,所以也是满足本体的要求。
import java.util.*;
public class Main {
public static void main(String agv[]) {
Scanner scanner = new Scanner(System.in);
int tableSize = scanner.nextInt();
Map<Integer, Integer> table = new HashMap<>(tableSize);
for (int i = 0; i < tableSize; i++) {
int key = scanner.nextInt();
int value = scanner.nextInt();
if (table.containsKey(key)) {//treeMap可以用getOrDefault对相同的key进行追加值的操作,hashmap只能自己进行判断是否有这个key
table.put(key, table.get(key) + value);
} else {
table.put(key, value);
}
}
for (Integer key : table.keySet()) {
System.out.println( key + " " + table.get(key));
}
}
}
方法二,最开始就想到map,然后要自动排序,就可是使用treeMap,第二,用map自带的getOrDefault方法,如果根据key没有值,就用默认的0表示方法的值,如果能根据key找到对应的值,那么直接赋值。使用treeMap让数据在map中就已经按照键升序的顺序进行排列了。
import java.util.*;
public class Main {
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
TreeMap<Integer,Integer> map = new TreeMap<>();
while(sc.hasNext()){
int n = sc.nextInt();
for(int i =0;i<n;i++){
int key = sc.nextInt();
int value = sc.nextInt();
map.put(key,map.getOrDefault(key,0)+value);
}
for(Integer i : map.keySet()){
System.out.println(i+" "+map.get(i));
}
}
}
}
8.提取不重复的整数
描述
输入一个 int 型整数,按照从右向左的阅读顺序,返回一个不含重复数字的新的整数。
保证输入的整数最后一位不是 0 。
数据范围: 1 \le n \le 10^{8} \1≤n≤108
输入描述:
输入一个int型整数
输出描述:
按照从右向左的阅读顺序,返回一个不含重复数字的新的整数
示例1
输入:
9876673
输出:
37689
import java.util.*;
public class Main{
public static void main(String args[]){
Scanner sc=new Scanner(System.in);
while(sc.hasNext()){
//使用HashSet来判断是否是否是不重复的
HashSet<Integer> hs=new HashSet<>();
int target=sc.nextInt();
while(target!=0){
int temp=target%10;//通过模10得到最后一位
if(hs.add(temp)){//如果能加入,则说明这个数字没有重复
System.out.print(temp);
}else{}
target/=10;//除10能去掉最右边的数字
}
System.out.println();
}
}
}
9.字符个数统计
描述
编写一个函数,计算字符串中含有的不同字符的个数。字符在 ASCII 码范围内( 0~127 ,包括 0 和 127 ),换行表示结束符,不算在字符里。不在范围内的不作统计。多个相同的字符只计算一次
例如,对于字符串 abaca 而言,有 a、b、c 三种不同的字符,因此输出 3 。
数据范围: 1 \le n \le 500 \1≤n≤500
输入描述:
输入一行没有空格的字符串。
输出描述:
输出 输入字符串 中范围在(0~127,包括0和127)字符的种数。
示例1
输入:
abc
输出:
3
示例2
输入:
aaa
输出:
1
//大佬言:凡是涉及到去重统计都可以用位图实现。因为每一个不同的数据只需要用二进制的一位存储即可,大大减小了统计所使用的存储空间
import java.util.Scanner;
import java.util.BitSet;
public class Main {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
String line = scanner.next();
//总共有128个字符。字需要用128位
BitSet bitSet = new BitSet(128);
for (char c : line.toCharArray()) {
//判断字符c是否已出现
if (!bitSet.get(c)) {
//未出现就设置为已出现
bitSet.set(c);
}
}
//统计有多少字符已出现过
System.out.println(bitSet.cardinality());
}
}