同事工资 2.5w,外企苟了9年,今年35岁,本来已经准备被裁,开始面试。结果一直裁不到,反而拿到阿里 offer涨薪50%~
刚看到个贴子,说有位网友同事在外企苟了9年,35岁,本来都准备躺平等裁了,结果愣是裁不到,反倒在面试时拿到阿里 offer,直接涨薪50%,现在反而纠结得不行。
外企稳,但天花板肉眼可见;阿里薪资高,可压力也不会小,就像从舒适区跳进深水区,能不能游得动,全看心态和身体。
35岁能拿到大厂 offer,本身就是实力的体现。纠结正常,但别让“年龄焦虑”绑架了选择。钱多当然香,但长期能不能接受强度、对职业路径有没有帮助,也得掂量。
总之还是那句话:职场不是选最好的,而是选最适合自己的。只要方向选对了,路怎么走都不亏。【备注:文末可领最新资料】
面试题:字符串解码
我那天晚上加班到十一点多,准备收拾电脑走人,结果我们组小李微信问我:“哥,那个字符串解码的题你咋写的?我写着写着脑袋就乱了。”我一看题目,哦,经典面试题那个——"3[a2[c]]" 要解码成 "accaccacc",就是今天要聊的这个。
先把题目说清楚
大概长这样:
输入是一个只包含数字、字母、 [、]的字符串格式像: 3[a]2[bc]、3[a2[c]]、10[ab]x这种数字表示后面那段在 []里的字符串要重复多少遍可以嵌套,可以多位数字
比如:
3[a]2[bc]→aaabcbc3[a2[c]]→accaccacc2[ab3[c]]x→abcccabcccx
核心就是:一边从左往右扫,一边把“当前构造的串”和“当前的倍数”给记住,遇到 [、] 再进出栈。
怎么想这个过程?
你可以脑补自己在手动算:
看 3[a2[c]]:
看到
3,先记住这是个次数,等着用看到
[,说明一个新的小世界要开始了,把刚才的“次数 3”和“此刻已经拼好的字符串(空串)”都压起来然后在这个小世界里,从
a2[c]开始继续扫
先是 a,当前字符串就变成"a"再遇到 2,先记住 2再遇到 [,又是一个更小的小世界,把当前"a"和 数字2再压一层进到 c,当前就是"c"遇到 ],这个小世界结束了,把刚才的"c"按次数 2 拼成"cc",再接到外面保存的"a"后面,变成"a" + "cc"="acc"
再遇到外面那层 ],说明大世界也结束了,把 "acc" 按最外层次数 3 拼接,就成 "accaccacc"
你会发现,每次遇到 [ 就“入栈”,遇到 ] 就“出栈并展开一次”,其他时间就是追加字母或构建数字。
用两个栈就够了
实现的时候,一般用:
一个栈存「重复次数」:
Stack<Integer> countStack一个栈存「之前的字符串」:
Stack<StringBuilder> strStack再加上两个“当前变量”:
curNum:当前正在读的数字(注意要处理多位数字,比如10[a])curStr:当前这一层正在拼的字符串
大致流程口水版说一遍:
字符是数字,就更新
curNum = curNum * 10 + (ch - '0')——这样1、0变成10字符是字母,就
curStr.append(ch)字符是
[:
把当前的 curNum压到countStack把当前的 curStr压到strStack然后 curNum归零,curStr换成新的空StringBuilder,准备进入新一层
字符是 ]:
从 countStack弹出一个次数k从 strStack弹出之前那层已经拼好的字符串prev在一个新的 StringBuilder里,把当前curStr重复k次拼上去然后把这个结果接到 prev后面,赋值回curStr = prev.append(repeated...)
最后扫完一遍,curStr.toString() 就是答案。
Java 实现直接给你一份
publicclassDecodeString{
public String decodeString(String s){
// 栈:保存“倍数”和“之前的字符串”
Deque<Integer> countStack = new ArrayDeque<>();
Deque<StringBuilder> strStack = new ArrayDeque<>();
StringBuilder curStr = new StringBuilder();
int curNum = 0;
for (int i = 0; i < s.length(); i++) {
char ch = s.charAt(i);
if (ch >= '0' && ch <= '9') {
// 多位数字处理,比如 10[a]
curNum = curNum * 10 + (ch - '0');
} elseif (ch == '[') {
// 进入新的一层,当前状态先保存
countStack.push(curNum);
strStack.push(curStr);
// 重置当前层
curNum = 0;
curStr = new StringBuilder();
} elseif (ch == ']') {
// 当前这层结束,展开一次
int repeat = countStack.pop();
StringBuilder prev = strStack.pop();
StringBuilder temp = new StringBuilder();
for (int k = 0; k < repeat; k++) {
temp.append(curStr);
}
// 接回上一层
curStr = prev.append(temp);
} else {
// 普通字符,直接追加
curStr.append(ch);
}
}
return curStr.toString();
}
// 随便测两下
publicstaticvoidmain(String[] args){
DecodeString d = new DecodeString();
System.out.println(d.decodeString("3[a2[c]]")); // accaccacc
System.out.println(d.decodeString("2[ab3[c]]x")); // abcccabcccx
System.out.println(d.decodeString("10[a]")); // aaaaaaaaaa
}
}
再啰嗦两句复杂度
每个字符最多进一次栈、出一次栈,时间复杂度差不多就是 O(n) 用到了两个栈,空间复杂度也是 O(n),主要花在栈和结果字符串上
如果你更喜欢递归,也能写成递归版本,思路其实一样:遇到 [ 就递归进去,遇到 ] 就返回。但在面试里,非要二选一的话,我一般更倾向上面这个双栈版,可读、也不太容易写炸。
好了,差不多就这样,你可以先照着敲一遍,再自己改一改变量名、自己手推一两个例子,基本这题就拿下了。
-END-
我为大家打造了一份RPA教程,完全免费:songshuhezi.com/rpa.html