登录后可回复主题
您需要 登录 才可以下载或查看,没有帐号?注册账号
x
关注我们:杭州上岸算法网络科技有限公司: o' K- I S! `* p0 ^
【 NO.1 可以输入的最大单词数】
9 l- o0 H: a+ O4 ]
% A" e: C0 l2 w$ O7 n解题思路: \0 d* ?) c1 N N" ?; n S; E
签到题,循环遍历判断即可。4 Q0 }5 R- s+ A
. |' ~ t! U6 b: _! }. w6 g/ P) v代码展示# p- l& t+ N- _3 Y" \" {$ M
4 y+ c; M8 O2 h$ `! M4 d) Kclass Solution {5 a" j9 O2 w' r3 Q6 N7 ?9 J
public int canBeTypedWords(String text, String brokenLetters) { H& x* X) D! {0 r0 B# F
if (text == null || text.length() == 0) {
{- o( e- @. }! B return 0;2 H: w; k- ?0 n1 r
}
; T' H& v) [2 _% { String[] texts = text.split(" ");
6 Z2 Y# x4 t6 D: ]6 v Set<Character> set = new HashSet<>();0 X4 Q. @9 N! p+ {
for (char c : brokenLetters.toCharArray()) {! e) u: O1 U+ ?2 c# F
set.add(c);
7 B! n1 A. r( P: K- V( s( u/ l; |! V }
/ _- f+ | `; ~5 c int ans = 0, flag = 0;
0 b5 Z7 U. o. T2 m5 Q; l for (String word : texts) {
& @0 ]) z0 S9 R7 i. Y' b+ {3 _% [ for (char c : word.toCharArray()) {
h# `" C- F( l! j& p& E if (set.contains(c)) {
+ U: |) |( b b# a& `( ^: \+ {+ H flag = 1;
' [) a m* S% k break;
+ n3 r A5 j* B0 P }6 y/ T3 ~3 I& y' @
}
, e. E$ a0 `/ |# r+ z if (flag == 0) {
5 a$ P8 @2 }( e# u, V ans++;5 N6 q- L6 a$ {3 C: h6 p" E
}4 ~0 {! u; }4 k% Z9 c. C% t2 j
flag = 0;6 F2 d4 p8 Y: y( t6 L
+ ~7 z; D0 ~* Y. j7 _1 t0 Q
}
" ]1 i" f0 {9 L# t7 I5 x return ans;
+ \3 j9 G6 c& z9 Z- }/ I }
8 l8 M# I* @- o w2 F- Q4 c5 ]}
/ r' g% H7 V: @: h* x- B m& p/ }+ i) P) S; m+ D( _3 v
【 NO.2 新增的最少台阶数】
- }7 w7 X# X6 l5 M, a) c9 c( Z1 J5 x( [' p& d. E) o
解题思路
6 _0 s \( ^( X& {0 b0 Z第二道签到题,两两计算差值,需要判断一下是否可以整除。
@# d+ ?/ ~: V, {6 ~. R
7 B6 N7 V4 C) ~0 |: q4 B代码展示
0 L5 h( k6 T+ f, s3 D
- _+ P/ W4 ^5 ?% y! g- p2 Sclass Solution {
$ T# ~. I1 s7 T h6 r* Q public int addRungs(int[] rungs, int dist) {& @ D- ^! G" d' j1 h
if (rungs == null || rungs.length == 0) {
/ w" B1 T2 j2 n8 e return 0;0 Q& E# `5 V) D3 m( h0 w9 n- ~5 M5 ^
}/ M& k" o8 F, N8 N+ x# C- p
int ans = 0;0 [. \3 z2 _$ Z! g2 O" g
int preRun = 0;6 B. ]3 ]$ q' G) ]; F
for (int rung : rungs) {, P; P$ h+ u. t' {/ K; _5 {( I" ~
int diff = rung - preRun;
1 V7 m8 o5 ~' Y( }# D V$ X6 F& p // 整除的情况可梯子少一个
# x$ N. j/ v5 L if (diff % dist == 0) {( u% _# q+ ?8 d' O, F
ans += diff / dist - 1;
# n3 E& u& F, K$ ~7 W } o' Y8 K! v1 |
else {9 Q, q1 r# o i" o3 k6 Y
ans += diff / dist;
* H7 {7 }* K' N9 S( \% x }
* p" G! m- D- S. u2 m preRun = rung; y' B7 V, O, Z3 A7 @: d8 f- I
}
. I6 s9 ]9 S8 m" }* c) r2 u( X return ans;8 M$ A5 p n; G* x
}
7 z: [9 t- m) z/ I3 _}: [9 U+ Q+ \& a0 H$ x; P! v* ~. t
7 E2 l, }/ b+ a' ~+ r
+ }! A4 y# V) d' X c: Z【 NO.3 扣分后的最大得分】
! t* L2 b/ W0 v* K9 r7 p8 Z# g" K# `# H
解题思路
# w& a9 a9 [/ r4 u7 G: j坐标型动态规划
+ R, Y9 T0 V9 s$ F- t
$ J; a! `& m/ f/ B8 Vdp[i][j]表示处于坐标 i j 的位置的最大收益
, N- F8 L4 g3 w7 Y* {4 B! l& }4 U7 \( z( A g/ G Q
普通的坐标转化会超时# ^' O. g& F( @. H7 r6 j
+ }7 k/ \# @! C* Z# r+ R4 E9 V考虑针对每一个j,会从 j的左侧和右侧转移过来,我们只想要一个收益最大的
6 o* R' ]' _$ s, h5 ]
( N, X7 L" u. ~& @/ X( w6 t% ^因此在遍历 j 的时候记录这个左侧和右侧最大的收益,给下一层用0 E% G; t, l6 X- X
/ I! q( W' O7 K# I0 W- F) _还有优化的空间,i 可以压缩成两行
+ O; u( h/ a4 N; p3 ~& A, L( \5 i! b* e+ S6 {3 Q* F, Z1 M U# P
代码展示
" J8 \5 t+ l; c" r. P0 V* S2 {! z c* Y7 X
class Solution {7 s% k% s9 Q6 l: [
public long maxPoints(int[][] points) {7 L9 c: O/ u2 m
if (points == null || points.length == 0 || points[0].length == 0) {0 Z2 ~2 Q5 H& n4 a& O1 r( f. U3 r
return 0;3 o" w* |, V- w! t
}0 a- D- x1 d' P. A5 {7 X C6 o) x
int n = points.length;
+ N' F8 q0 i2 \ int m = points[0].length;
" n9 C$ e# Y+ | long[][] dp = new long[n][m];
" a& P3 M' I9 F h5 q // 首行初始化2 Q. k. \# F, M0 }
for (int j = 0; j < m; j++) {
, k p* X1 y9 ^7 ^+ y1 X dp[0][j] = points[0][j];
* v0 B3 H. b$ @: D. {+ Q }
* y+ j) a0 `8 r' s for (int i = 1; i < n; i++) {5 @; [8 I$ [+ l @ m
// 对于所有上一行左边的数,都是加上它的坐标减去自己的坐标;4 ~+ A. I, V; Y. H6 w
// 对于上一行所有右边的数,都是减去它的坐标加上自己的坐标;
8 T. ^+ m. v2 \, M long leftMax = Integer.MIN_VALUE;
. y, ?4 K" N& p; ?1 v3 {$ [ long rightMax = Integer.MIN_VALUE;
. h0 T4 L( J1 i- M+ u- S" M6 q for (int j = 0; j < m; j++) {
. A, a$ f" B& Q0 Q# ~5 @! ^, z7 p leftMax = Math.max(leftMax, dp[i - 1][j] + j);; a- ~7 |5 z; u
rightMax = Math.max(rightMax, dp[i - 1][m - 1 - j] - (m - 1 - j)); ]: V- l2 O" n
dp[i][j] = Math.max(dp[i][j], points[i][j] + leftMax - j);3 L+ ^& i5 E/ D' A
dp[i][m - 1 - j] = Math.max(dp[i][m - 1 - j], points[i][m - 1 - j] + rightMax + m - 1 - j);
4 X+ c( [5 j" c; ^ }
6 |' u2 [1 Q$ e1 a* h }0 S. t+ \. e2 d/ u+ F6 M( F$ n2 j8 o( u
long ans = 0;- W+ P, Q+ M4 v4 V
for (int j = 0; j < m; j++) {& X- V/ W! j. f8 s f
ans = Math.max(ans, dp[n - 1][j]);1 d/ O3 f' _& R! Y' b; Y$ E
}$ N5 T% i- a% h. L# [- D5 F$ Z, m
return ans;
# v9 c' G5 r- ?$ g, D7 V$ r }3 N3 j7 n5 s2 I1 G* P
}
: R' C+ y+ G* f" E- a
* s& A/ P5 G [$ k0 V- ~2 v$ i
: X0 O7 [0 d! E! r【 NO.4 查询最大基因差】
6 [ a* S' h) U$ h' c0 V. E7 ^3 p, }" y* N' w s
解题思路
" q, \0 z" o& O# O# G! X二进制的字典树:将数字转化成二进制记录在字典树当中8 l# O$ l, J* w0 n9 }0 @5 a
' J% X9 s$ ^# K3 }# X3 Q构建树,方便做DFS! }8 }% Y! _! J& D( ]. ~
% i0 H- w6 n: r# J$ x4 @& ~ t每搜索一个数字,将该数字更新到字典树当中$ q' W5 x8 w4 z9 g4 L H
! u: b' {' Y: s' b* w在字典树上计算最终最大的异或值
8 E* U- |% a2 ]! \9 [3 G# g& [ M( }9 C3 Q/ [
代码展示6 }9 C) K+ B: I' b, r @4 O
0 M- r3 e3 G$ k7 q
class Trie {
" x% F$ J* V6 n5 F9 T2 G Trie left; // 1
1 i4 K6 C3 b- `! b, I1 ]9 P- [ Trie right; // 0# E- F% ?0 r: i. w) x6 B
int[] count = new int[2];
/ D( t! k @" o( i public Trie() {}
& I, K |5 u3 N1 h9 y
& Y; U7 ^% u0 P. A% O // s == 1 添加, s == -1 删除, i l8 W# n. C5 W
public void insert(int val, int s) {
4 A& g# g E1 R- q, x* B' h int flag = (1 << 30);* s' V- Q E, ]/ o
Trie node = this;
* Q* X5 O& V9 Z2 @$ H while (flag > 0) {
: j/ W. u* C# q n4 v) M int bit = (flag & val);
0 d% j3 S' [! C4 _ if (bit > 0) {
5 n0 ?; m& _3 a$ D6 t- t // 1 走左边
6 f! c% [2 q7 N2 t7 p if (node.left == null) {- @. t2 F+ u, w' I" G+ G+ A
node.left = new Trie();
* z: J! o8 X7 ^. ` }
: \& o0 F8 ?$ @) O; r! L node.count[1] += s;
$ O5 e& I' O+ E6 N4 d node = node.left;
- L8 u) V4 m3 m$ ^ } else {
7 N; F- M3 M# o/ L8 v // 0 走右边
) i) E3 d; ^4 ]& l, S$ T5 T) E if (node.right == null) {
3 F! o' A* E% v$ G) h. ` node.right = new Trie();4 q# v+ W- n3 e5 N
}7 B, U. Z/ A! x9 @
node.count[0] += s;
8 e1 S: X# X4 j5 t+ `2 |# z node = node.right;
' i+ T. J# w" e$ |1 X& ~; d" z }& x# X/ d# K/ O6 l E ?/ T' S
flag >>>= 1;* R- A# @5 v9 d9 T) r+ @, T
}/ c6 j* n5 @3 m- m' D. ?
}6 ]0 m- \3 r- s8 |( t, Z
) ~9 `1 e0 x' I) @* D
public int getMax(int val) {
! u; D5 D, G. M# }9 D& \4 y Trie node = this;
. V- [: `- {; v6 h int flag = (1 << 30);
: Q; Z( B3 ~/ S$ K int res = 0;
2 O( M- E( d/ R3 ]" \# h while (flag > 0) {! P! y" a. @& F5 L
int bit = (flag & val);
' H% q1 o6 h5 w7 }- m' A- K // 贪心算法,1 的话走右边,0 的话走左边
1 H& a( Z$ [# T1 e" G if (bit > 0) {( [0 h- k3 B3 O& o9 E' W$ H
// 走右边,右边不行走左边
- P3 e& H0 A0 F if (node.right != null && node.count[0] > 0 ) {7 R" ?( i! Z9 [ G- F. B* q$ ~
node = node.right;" T% {2 z; p. V& Q- j0 G
res |= flag;9 E) h1 g6 Q- b/ o; Y
} else if (node.left != null && node.count[1] > 0) {
. r' k6 j5 z$ `* S; W node = node.left;3 C8 y. h( F( R7 A1 r6 s" T2 \
} else {5 Y1 Y( F6 N4 h. l E
return -1;
7 c3 ]5 w, N1 e5 r; t }
* d5 x$ y9 F5 k" o& n) E } else {
4 C; a3 ]" ~; {( p% i* ~: U/ B/ f // 优先走左边: ~& h+ R" k* \5 _! O5 B8 m
if (node.left != null && node.count[1] > 0) {
: m- D5 O" {" u node = node.left;4 F" ?+ ` K1 L, D" b5 D
res |= flag;( N7 s, Q( |, I. E' ^" C
} else if (node.right != null && node.count[0] > 0) {
. U+ `% H5 j0 ~ node = node.right;/ W0 W, F7 `; [5 y' i4 p
} else {4 V% f( ]1 x% {& j/ a
return -1;( E$ M' }; N4 f f$ p! V( c5 D
}' C ]5 E* B1 m. B ]) x
}
9 M- V( |: P8 Z( v/ E7 j- K3 _ flag >>>= 1;* Z; Z. E% u1 g8 o
}
1 k; e$ `; c: V, W* v return res;
) Y6 g. ?, t1 d, B. D }1 W/ J& g. a3 h+ G
}& r3 l0 {+ Y% C. T( D4 r
public class Solution2 {
* {6 C- j1 F/ M8 Q. Z static class TreeNode {) V, Z5 M4 [/ H& \" R) |
List<TreeNode> son = new ArrayList<>();
- H6 `! I% J6 q6 l7 @: ?4 S; ^# u0 z int val; E3 R% Z. y, I$ G5 B" }
public TreeNode(int val) {
, L7 t- f9 x. B: ~$ F( O this.val = val;
, e0 w# L& q6 @7 z1 ~8 {+ V }
4 y0 b* R, ]% U. N4 ? }& R9 P' W4 x3 D. j @
Map<Integer, List<int[]>> map = new HashMap<>();
% c; q$ ^: A1 r8 | Trie trie;
; A: j$ L6 Z5 j8 w/ {0 E7 r2 A public int[] maxGeneticDifference(int[] parents, int[][] queries) {" k$ `6 k; i, Q1 n+ Y" D! B, H7 n
int n = parents.length, m = queries.length;
X' c8 U% ^ l$ N" {4 F // 封装查询的信息. I5 L( \7 X# x: D1 \
for (int i = 0; i < m; i++) {/ _6 |8 f* s' O$ S% Q+ a
int node = queries[i][0], val = queries[i][1];
. M( ?2 C0 ^: O0 M if (!map.containsKey(node)) {
7 v. d- _- g1 F- s, t4 n map.put(node, new ArrayList<>());
5 |1 P% j/ V6 e4 X3 P( D }
4 a. L" A1 t4 {& O+ h2 [9 _ map.get(node).add(new int[]{val, i});
! | H8 r. b+ p/ g+ G' I4 ]8 I L- \ }. n* h1 Y: z1 @; Y/ n! N! B
Map<Integer, TreeNode> nodeMap = new HashMap<>();
# t- W6 l) d: P // 构建树
" J. H$ \6 i& T2 |- J: e- b9 G TreeNode root = null;: Y; Q7 g7 a4 f# c
for (int i = 0; i < parents.length; i++) {
9 x! @% K! r- c" Y2 y7 \4 a int p = parents[i];+ L& h1 x$ [( k* K+ r0 g5 U
if (!nodeMap.containsKey(i)) {# `; K) {3 l% \+ C1 \; x
nodeMap.put(i, new TreeNode(i));0 t! j+ G. w4 y9 Q, h
}
1 F" P$ L1 j& C8 P t' a- M6 c+ f if (p != -1) {
: u: t% |: r) ~2 j' n* o/ a if (!nodeMap.containsKey(p)) {* W0 |5 [5 @! M0 T$ N
nodeMap.put(p, new TreeNode(p));
5 E: E' v4 B, ?; v6 L }
, Z# F5 ?( j- F9 V) B nodeMap.get(p).son.add(nodeMap.get(i));: X0 G9 A$ Y* c, N' ?' ?
} else {
/ p @- s3 p }0 s$ b0 t T7 o root = nodeMap.get(i);
$ Y; b# K# o" S }
1 U, D& h/ J! I a! m: r& j, N }$ _: x; Y% m. E7 h1 ?: _) g0 g
trie = new Trie();8 ?& F) _& d% Z {, j+ S5 i1 r c
int[] res = new int[m];
! Z2 u+ o0 U5 t0 @' ? // 在树上进行DFS
; D+ r5 c8 Z3 i( n' ] dfs(root, res, map, trie);
8 I; h; @# {# M2 e% p return res;- r. I: h- Q. l" t7 k! r# i5 Z
3 B( k7 m8 ^- | }* C4 e$ ^, ^7 d" w! Q
8 l% F- L' z9 k) n" }; y- I9 A* T
private void dfs(TreeNode root, int[] res, Map<Integer, List<int[]>> map, Trie t) {
! K' K# @8 S; r6 z if (root == null) {
6 l* z1 [* T9 Z w' ~% {% @ return;: V5 g f( g1 t/ r! @/ N/ e3 V/ [
}! q5 X$ P# G7 g: v# t
t.insert(root.val, 1);
& ~7 {( ?/ y y( C- w if (map.containsKey(root.val)) {
% E, z" f8 U4 G: A* K for (int[] each : map.get(root.val)) {7 D. H2 _ Y0 X$ N6 [6 |; s
int idx = each[1], v = each[0];
9 A( e3 X$ a: c' v res[idx] = t.getMax(v);
2 J0 [2 a! U% U) }$ f }
8 v' r" ~% l7 e! R- V }
2 _ l, h- E3 v9 P% i; Z# G for (TreeNode s : root.son) {
" C. R9 [# y2 h' v+ y dfs(s, res, map, t);
6 {8 j6 l' m5 S! x }
- \7 t$ A) |6 g! w- E/ i. F( A // delete
$ l" T B; R" @5 Y7 X; y t.insert(root.val, -1);
+ q2 n: e7 E" ]3 y8 q ^( R }
4 P: g! M; R T, y1 h}
) i% g4 ^/ `( w2 ^" w
; _& z9 b( F) s- h/ \$ ?7 q; ?2 v9 N! a
|