题目一: TLV编码
TLV编码是按 Tag Length Value格式进行编码的一段码流中的信元用tag标识,tag在码流中唯一不重复
length表示信元value的长度 value表示信元的值
码流以某信元的tag开头 ,tag固定占一个字节
length固定占两个字节,字节序为小端序
现给定tlv格式编码的码流以及需要解码的信元tag
请输出该信元的value
输入码流的16机制字符中,不包括小写字母
且要求输出的16进制字符串中也不要包含字符字母
码流字符串的最大长度不超过50000个字
输入描述
第一行为第一个字符串 ,表示待解码信元的tag
输入第二行为一个字符串, 表示待解码的16进制码流
字节之间用空格分割
输出描述
输出一个字符串,表示待解码信元以16进制表示的value
例子:
输入:
31
32 01 00 AE 90 02 00 01 02 30 03 00 AB 32 31 31 02 00 32 33 33 01 00 CC
输出
32 33
说明:
需要解析的信源的tag是31
从码流的起始处开始匹配,tag为32的信元长度为1(01 00,小端序表示为1)
第二个信元的tag为90 其长度为2
第三个信元的tag为30 其长度为3
第四个信元的tag为31 其长度为2(02 00)
所以返回长度后面的两个字节即可 为 32 33
- 代码如下
import java.util.*;
public class Test4 {
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
String tag = sc.nextLine();
String[] split = sc.nextLine().split("\\s+");
for(int i=0; i<split.length; ){
int len = Integer.parseInt(split[i+2]+split[i+1],16);
if(tag.equals(split[i])){
StringBuilder bu = new StringBuilder();
for(int j=i+3; j<i+3+len;j++){
bu.append(split[j]).append(" ");
}
System.out.println(bu.toString());
break;
}
else{
i+=len+3;
}
}
}
}
题目二:字符串target和source
给定字符串target和source,判断target是否为source的子序列。你可以认为target和source 中仅包含英文小写字母,字符串source可能会很长,
长度~=500,000,而target是个短字符串,长度<=100。字符串的一个子序列是原始字符串删除一些(也可以不删除)字符而不改变剩余字符相对位置
形成的新字符串,例如,'abc’是’aebycd’的一个子序列,而’ayb’不是。请找出最后一个序列的起始位置。
示例1
输入:
abc
eadbc
输出:
1
示例2
输入:
abc
abcaybec
输出:
3
说明:abcaybec中第0位的abc也匹配,但却不是最后匹配的序列。abcaybec中第3位的aybec去掉字符y、e后也为abc,也与目标字符串相符,故输出最后一个序列aybec的第一个字符的索引位置3。
- 代码如下
package com.winyar.algorithm.od;
import java.util.Scanner;
/**
* @Describe 判断字符串子序列
* @Author Winyar
* @Date 2022/6/18
*/
public class SubSequenceLastIndex {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
while (sc.hasNextLine()) {
String target = sc.nextLine();
String source = sc.nextLine();
int targetLen = target.length();
int sourceLen = source.length();
int i = targetLen - 1;
int j = sourceLen - 1;
// 标识是否有匹配的子序列
boolean flag = false;
// 逆序遍历
while (i >= 0 && j >= 0) {
if (target.charAt(i) == source.charAt(j)) {
if (i == 0) {
// 指针走到target第0位,说明能够匹配完目标字符串
flag = true;
System.out.println(j);
}
i--;
j--;
} else {
// 没有找到相等的字符,继续向左遍历source字符串
j--;
}
}
if (!flag) {
System.out.println(-1);
}
}
sc.close();
}
}
题目三 华为od欢快的周末
小华和小为是很要好的朋友,他们约定周末一起吃饭通过手机交流,他们在地图上选择了多个聚餐地点(由于自然地形等原因,部分聚餐地点不可达),求小华和小为都能到达的聚餐地点有多少个?
输入描述:
第一行输入m和n,m代表地图的长度,n代表地图的宽度。第二行开始具体输入地图信息,地图信息包含:
- 0为通畅的道路
- 1为障碍物(旦仅1为障碍物)
- 2为小华或者小为,地图中必定有且仅有2个(非障碍物)
- 3为被选中的聚餐地点(非障碍物)
- 代码实现
public class FunnyWeeks {
static final int N = 110;
static int[][] arr = new int[N][N];
static Map<String, Integer> map1 = new HashMap<>(),map2 = new HashMap<>();
static int[] dx = new int[]{-1, 0, 1, 0}, dy = new int[]{0, 1, 0, -1};
static int n, m;
public static void main(String[] args) {
Scanner cin = new Scanner(System.in);
n = cin.nextInt();
m = cin.nextInt();
int[] pos = new int[4];
for (int i = 0,k = 0; i < n; i++) {
for (int j = 0; j < m; j++) {
arr[i][j] = cin.nextInt();
if(arr[i][j] == 2) {
pos[k++] = i;
pos[k++] = j;
}
}
}
dfs(pos[0],pos[1],map1);
dfs(pos[2],pos[3],map2);
int res = 0;
if(map1.size() == 0 || map2.size() == 0) System.out.println(0);
else {
for(Map.Entry<String,Integer> entry : map1.entrySet()) {
String key = entry.getKey();
if(map2.containsKey(key)) res++;
}
System.out.println(res);
}
}
public static void dfs(int x, int y,Map<String,Integer> map) {
if (arr[x][y] == 3) {
String key = get(x,y);
map.put(key, map.getOrDefault(key, 0) + 1);
return;
}
int k = arr[x][y];
arr[x][y] = -1;
for (int i = 0; i < 4; i++) {
int a = dx[i] + x, b = dy[i] + y;
if (a >= 0 && a < n && b >= 0 && b < m && arr[a][b] != 1 && arr[a][b] != -1 && !map.containsKey(get(a,b))) {
dfs(a, b,map);
}
}
arr[x][y] = k;
}
public static String get(int x,int y) {
return String.valueOf(x) + "@" + String.valueOf(y);
}
}
文章来源地址https://www.toymoban.com/news/detail-627949.html
文章来源:https://www.toymoban.com/news/detail-627949.html
到了这里,关于华为OD-机试(三道)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!