注册
环信即时通讯云

环信即时通讯云

单聊、群聊、聊天室...
环信开发文档

环信开发文档

环信FAQ

环信FAQ

集成常见问题及答案
RTE开发者社区

RTE开发者社区

汇聚音视频领域技术干货,分享行业资讯
技术讨论区

技术讨论区

技术交流、答疑
资源下载

资源下载

收集了海量宝藏开发资源
iOS Library

iOS Library

不需要辛辛苦苦的去找轮子, 这里都有
Android Library

Android Library

不需要辛辛苦苦的去找轮子, 这里都有

这两年,我把28年以来欠的亏都吃完了...

前言 很长一段时间没有总结一下过去几个月的状态了,今天思绪万千,脑海中浮现了很多经历和生活片段,我把它记录下来。顺便今天聊一聊认知突破,分享我在买房这段时间吃过的亏,也希望作为你的前车之鉴。 买房 21年底的时候,那时刚好毕业三年,也正是互联网公司996最流行...
继续阅读 »

前言


很长一段时间没有总结一下过去几个月的状态了,今天思绪万千,脑海中浮现了很多经历和生活片段,我把它记录下来。顺便今天聊一聊认知突破,分享我在买房这段时间吃过的亏,也希望作为你的前车之鉴。


买房


21年底的时候,那时刚好毕业三年,也正是互联网公司996最流行的阶段,由于平时我不怎么花钱,也很少买衣服,上网买东西是个矛盾体,需要花很多时间对比,经常看了一件东西很久,最后又不买。加上比较高强度的工作状态,两点一线,可以说是没时间花钱,再加上自己把钱都拿去理财了,也赚了几万块,最后一共攒了几十万下来。我从小就立志要走出农村,而且认为以后有女朋友结婚也要房子,加上当时花比较多时间在理财上面,那时候其实行情已经不好了,工作上没什么突破,比较迷茫,于是想着干脆就把钱花出去了,自己也就有动力去搞各种路子尝试赚钱。在没有经过任何对比之后就在佛山买了一套房子,房价正是高峰的时候,于是我成功站岗!因为这个契机,躲过了持续了2年多的低迷股市,却没躲过低迷的房地产。


while(true) { 坑++ }


我买的是期房,当时不知道期房会有这么多坑,比如期间不确定开发商会不会破产,我这个开发商(龙光)就差点破产了,房产证无着落,相当于花了200w买了一个无证的房子,这辈子就算是搭进去了。


对于整个购房过程也是很懵逼,对流程完全不熟悉,当时去翻了政府规划文件,看那个地段后续有没有涨价空间,然后跟着亲戚介绍的销售转圈圈,当时说给我免3年物业费,合计也有几万块。在签合同之前销售都有说可以给到,但由于第一次没有录音,导致在签合同的时候销售反口,不承认,我们也没有证据,最后吃了哑巴亏。


开始的时候谈好了一个价格167w,然后销售私下打电话给我洗脑说我给点辛苦费1.5w,他可以向领导申请多几万块优惠。我知道这是他们的销售套路,但是架不住给我优惠5w啊,中间反复拉扯最后说给他8k,采用线下现金交易的方式。这一次我有录音了,因为私底下交易没有任何痕迹,也不合法,所以留了一手,也成为我后面维权时争取话语权的基础。


中介佣金是很乐观的,当时由于我亲戚推荐我去,销售承诺税前有4w,当时看中这个返佣也促使我火急火燎的交了定金。现在3年过去了,这个佣金依旧没有到账,我一度怀疑是中介搞ABC套路把我这个钱💰吃了,其他邻居的推荐佣金都到了账,加上现在地产商没钱了,同时跟那个亲戚有些过节,这个返佣更是遥遥无期。最后通过上面的录音获得了一丝话语权,知道了这个钱还在开发商手上,一直没有拨款下来到中介公司。下面是部分聊天记录:


image.png


不接受微信语音沟通,文字可以留给自己思考的时间,同时也更好收集证据。


image.png


然后去找相关人员把信息拉出来给我看,显示开发商未付款状态,这个状态维持2年了,目前看来只能再等下去。


image.png


签合同的时候,有个律师所说是协助我们签合同、备案、办房产证等各种边缘工作,糊里糊涂交了700元律师费,不交不行,甚至律师所连发票都没有给,而我都没有意识到这个最基本的法律法规问题。现在交房了可以办理房产证了,拿证下来也就80块登记费,居然收我700,其他业主有些是600多,400多,顿时觉得智商受到了侮辱,看了网上铁头各种打假的视频,我觉得自己也应该勇敢发声。现在也在收集商家各种违规证据,提交给相关部门解决。


image.png


image.png


image.png


后面市场监督管理局收到投诉,应该是有协商,意识到没有给我们发票,过来几天之后才把发票补过来,开票日期不是付款时候的2022年,而是2024年,明显属于偷税了。目前跟他要发票的应该只有我,估算2300多户业主都没有开发票的。


当时我首付需要50w,自己手上不够,我爸干建筑一辈子,辛苦供我们两个孩子上了大学,山上建了两层楼,手里没钱。我妈是一辈子没打过工,消极派,说出来没几句好话,家里不和睦的始作俑者,更不可能有钱支持。所以我还有20w是首付贷,也就是跟开发商借的,利率10%,这个利息很高了。销售当时说可以优惠到5%,但是优惠金额是补贴到总房价里面去,其实这也是他们的一种销售套路,这亏我也吃了,2年之后我连本带息还24w。当时认为自己应该一年左右能还完,但是实际远远高估自己的能力,买完房子接着我爸又生病在医院待了几个月,前后花了十几万,人生一下子跌入了谷底。


从头再来


后面2023一年,我出去创业,模式很新,很多人不赞同,期间遇到了不少小人诋毁我们两夫妻,当时我老婆还在怀孕,但我们最后都熬过来了,还生了一个儿子,6斤多。期间一年赚了十几万,但是开支也大,加上父母要养,我爸还要吃药,房子要供,最后还是选择了先稳定下来,我重新回到了职场,空窗一年后在这个环境下拿了一个还不错的offer,同时也想自己沉淀一下。


自从有了宝宝之后,生活似乎都往好的方面发展,出版社找我出书,为了契合自己的职业发展,我选择了写书《NestJS全栈开发秘籍》,从2023年11月份开始,迄今快半年了,在收尾阶段,希望尽快与各位读者们见面。同时,等了3年的房子也收房了,由于是高层,质量相对其他邻居好,没有出现成片天花掉下来或者漏水的情况。我们经常都说他是天使宝宝,是来报恩的。


由于我们公司技术部门是属于后勤支持性质的,技术变化不大,Vue2+微前端和React管理系统那一套,没有太多的新技术扩展,意味着不确定也大。业务发展不好考虑的是减少这些部门的开支,所以不出意外最近也迎来了降薪。这不是最可怕的,对于我们技术人来讲,最可怕的是我认为在业务中成长停滞了,或者没有业务来锻炼技术,所以在业余时间也选择了参与一些开源项目,如hello-alog开源算法书的代码贡献,并且这也是选择写书的原因。很简单地说,当下一个面试官问到我的时候,我不可能什么都讲不出来,最经典的问题就是:在这个公司期间你做过最有成就感的事情是什么?现在,我有了答案!


哲学


我的人生哲学是不断改变,拥抱不确定性!这么看来,我的确在这些年上了不少当,吃了不少亏,把自己搞的很累,甚至连累到家里人。但,用我老婆经常说的一句话:人生这么长,总是要经历点什么,再说现在也没有很差。的确,不断将自己处于变化之中,当不确定性降临到普罗大众时,我们唯一的优势,就是更加从容


总结


人们还在行走,我们的故事还在继续~


WechatIMG154.jpg


作者:寻找奶酪的mouse
来源:juejin.cn/post/7349136892333981711
收起阅读 »

为啥微信的更新信息大多数都是:修复已知问题,但是开发中不建议这样。

背景 可能大家平常有意或无意的注意到,微信的更新日志经常是:解决了一些已知问题。 但是开发人员日常开发中,提交的信息一般会避免这样,反而会要求把提交信息写的比较详细。 原因 首先,从用户体验的角度来看,频繁地列出所有已知问题及其修复情况可能会让用户感到困惑或...
继续阅读 »

背景


可能大家平常有意或无意的注意到,微信的更新日志经常是:解决了一些已知问题。


image.png


但是开发人员日常开发中,提交的信息一般会避免这样,反而会要求把提交信息写的比较详细。


原因


首先,从用户体验的角度来看,频繁地列出所有已知问题及其修复情况可能会让用户感到困惑或担忧,尤其是当这些问题涉及到隐私、安全等敏感话题时。其次,微信作为一个庞大的社交平台,其功能众多,更新日志如果详细到每一项改动,不仅对普通用户来说难以理解,也会增加开发团队的工作量。此外,微信的更新往往伴随着大量的内部优化和结构调整,这些内容对于普通用户而言并不重要,也不易被察觉。


而对于开发人员来说,commit信息一是给自己以后看,通过提交信息就可以知道自己修改了哪些内容,其二就是给其他开发人员查看,从而知道别人修改了哪些地方。


查看提交日志


那么关于微信相关的我们不再赘述,主要针对开发人员的提交信息进行一些讨论,比如如何查看提交信息呢,在idea中可以直接查看git log,也可以通过命令git log来进行查看,或者也可以使用命令git show commitHash针对每一个提交信息进行详细的查看,例如:


$ git show 32557725d91403ca8e5ae520a5f82a516791f5c0
commit 32557725d91403ca8e5ae520a5f82a516791f5c0
Author: test1 <test1@some.com>
Date: Wed Mar 20 16:53:56 2024 +0800

b5 commit

diff --git a/b.txt b/b.txt
index 86bd041..be62feb 100644
--- a/b.txt
+++ b/b.txt
@@ -2,4 +2,6 @@
22222

33333
-44444
\ No newline at end of file
+44444
+
+55555
\ No newline at end of file

本人代码提交方式


关于代码提交规范,相关的文章有很多,我在此先不多说,只是把我平常所用到的描述一下,大家可以参考。


针对每次的功能涉及到几个方面:代码优化,新功能开发,bug修复等。



  • 针对新功能开发:一般是git commit xxxx.java -m 'feat:用户登录限制只允许特定IP地址来登录管理员账号'

  • 针对bug修复:一般是git commit xxx.java -m 'fix:用户登录后看不到自己的工作任务'
    针对

  • 针对代码优化:,则是git commit xxx.sql -m 'refactor:把原来不存在的用户显示为ID账号,而非null'


总结


其实写好commit信息有较多好处,不单单是上面提到的个人追溯问题容易以及同事协作简单。以下我列出来我想到的。



  • 通过commit信息方便自己进行日报周报的总结

  • 方便进行某些问题的回退

  • 方便快速的梳理功能,以便于线上环境的验证

  • 有益于自己代码的精简提交,如果多个文件一起提,那么commit信息可能就会更复杂


致谢


以上就是从微信的一个更新日志,进而针对开发人员的commit信息进行了一些简单阐述。感谢你的耐心阅读,如果我的分享对你有所启发或帮助,就给个赞呗,很开心能帮到别人。


作者:bramble
来源:juejin.cn/post/7351726029322928155
收起阅读 »

为什么很多程序员会觉得领导没能力

相信很多人在职场里待久了,都会遇到自己觉得比较差劲的领导,这些人可能除了向上管理能力很强外(会舔老板),其他能力在你看来都挺一般,专业能力一般,超级缝合怪--上级给他的任何任务他都能分配给你们,然后他再缝合一遍完事。 那么遇到这种领导我们该怎么办呢?多数人想到...
继续阅读 »

相信很多人在职场里待久了,都会遇到自己觉得比较差劲的领导,这些人可能除了向上管理能力很强外(会舔老板),其他能力在你看来都挺一般,专业能力一般,超级缝合怪--上级给他的任何任务他都能分配给你们,然后他再缝合一遍完事。


那么遇到这种领导我们该怎么办呢?多数人想到的是跳槽,这确实是一个解法,但你跳到下家公司也保不齐会有这样的领导呀,今天咱们讨论的这个话题就先把条件限定成你不能跳槽,这个时候你该采用什么方法让自己的上班体验变好一些。


多元化自己的评估标准


首先,不能用鄙视的眼光去看待你的领导,觉得他只会舔老板(能舔、会舔也是一种很强的能力呀),有的时候你觉得你领导能力不行,很有可能是因为你的能力评估标准太单一了。


他或许在工作的某个方面不如你,但是他必定在某些方面有自己的长处,努力发现他的长处,认可他的长处,学习他的长处,可以更有助于你和他的相处,也有利于你的进步。


社会是一个大熔炉,你需要的不仅仅是业务能力和展现的舞台,也需要与社会中不同个体的和谐共处。包容、接纳,都是立身处世的能力。


学会变通和沟通,满足领导的存在感


领导之所以会在很多工作上提意见、瞎指挥、乱指挥,更多的情况可能是他知道自己对工作不熟悉,但觉得自己是领导,会有自己独特的见解,想刷自己的存在感。这种情况下,要学会满足领导的存在感。


举个例子说,你在工作中,领导过来给你提了个意见,这个意见明显是不合适的,那你就可以说,“领导,这个思路好,我们之前没往这个角度想,可以从这个角度延展一下……。”他走了,还不是我们自己把控,毕竟他只是过来刷个存在感的,只要最后的方案让客户满意,业绩给领导,把一些光环放在他身上,让他觉得他起到了作用,这些方案和他有关,他通常也不会计较了。


摸清领导管理的思想和套路


说到这里,找到领导心中的关键因素,是非常必要的。在一个项目里,员工承担的通常只是局部,而领导看的是整体,由于高度不同,所以你们考虑的关键因素是不同的。


所以你要知道领导心里到底想要的是什么,提前做好这方面的预期和准备,以及针对领导提出的你们没有考虑到的方面要虚心接受(毕竟领导跟高层接触的更多,有些战略方向上的事情他们会更清楚)。 


比如说,你是一个小编,你在意的是按时完成写作任务、及时发表、赚取眼球,而你的领导主编可能更在意的是你文章的各种数据真实性、转化人群、是否会产生舆情、是否zzzq这些。所以,要搞清领导在意的重要维度,工作才能更有效。


这里有三句话分享给大家:



  • 要能够分清你可以改变的事、无法改变的事;

  • 不去抱怨你服务改变的事;

  • 把精力用在你可以改变的地方。


你的上司,是你改变不了的,但你自己,是可以把握的。当然这篇文章也不是教你怎么委屈自己,只是提供一个不同的角度来讨论"领导不行” 这个事情,以及让你在无法立刻更换环境时,该怎样让当前的环境变得不那么恶劣。


想跳槽的同学还是应该按部就班的准备,骑驴找马有更合适的地方该跳就跳,跳过去了说不定今天学到的这些还能用的上……。


作者:kevinyan
来源:juejin.cn/post/7357911195946336293
收起阅读 »

既然有需求,那么就手撸一个JSON可视化组件吧

前言: 最近在公司的一个项目中遇到了一个需求,就是将读取到的JSON数据,展示成一个树形结构,并且还得给每一个节点添加一个类型标签以及复选框。好了,话不多说,直接上代码,代码的思路到时候放在代码后面。如果各位看官老爷觉得有什么可以优化的地方或者不理解的地方也可...
继续阅读 »

前言:


最近在公司的一个项目中遇到了一个需求,就是将读取到的JSON数据,展示成一个树形结构,并且还得给每一个节点添加一个类型标签以及复选框。好了,话不多说,直接上代码,代码的思路到时候放在代码后面。如果各位看官老爷觉得有什么可以优化的地方或者不理解的地方也可以在评论中说出,大家一起讨论;


代码


<script>
export default {
name: "YJsonEditer",
data() {
return {
JsonAST: {},
LiList: [],
checkBoxList: [],
checkBoxKey: 1,
// checkId:''
};
},
props: {
json: {
type: String,
default:
'{"total":18,"data":[[{"themeType":{"themeType":"dark"}}],[{"themeType":"light"}]],"rows":[{"caseCode":"9174ff6dfbc243eb931270a06c447666","institutionId":2,"arbitralCourtId":1,"nickName":"张慧","deptId":102,"applicantName":"钱红","arbitralCourtName":"第一仲裁庭","times":2,"caseNumber":"常钟劳人仲案字〔2023〕第29号","scheduleDate":"2023-05-30T00:00:00","caseName":"钱红讨薪","respondentName":"钱橙","startTime":"08:30:00","id":26,"endTime":"08:45:00","status":"1"},{"caseCode":"1c096b703b78495ea90ca13ab65258cb","institutionId":2,"arbitralCourtId":1,"nickName":"徐洋","deptId":102,"applicantName":"赵春","arbitralCourtName":"第一仲裁庭","times":1,"caseNumber":"常钟劳人仲案字〔2023〕第28号","scheduleDate":"2023-05-25T00:00:00","caseName":"赵春徐洋登记","respondentName":"赵夏","startTime":"08:30:00","id":24,"endTime":"08:45:00","status":"3"},{"caseCode":"9174ff6dfbc243eb931270a06c447666","institutionId":2,"arbitralCourtId":1,"nickName":"张慧","deptId":102,"applicantName":"钱红","arbitralCourtName":"第一仲裁庭","times":1,"caseNumber":"常钟劳人仲案字〔2023〕第29号","scheduleDate":"2023-05-25T00:00:00","caseName":"钱红讨薪","respondentName":"钱橙","startTime":"09:00:00","id":25,"endTime":"09:15:00","status":"3"},{"caseCode":"47cdbb573f354660b448d3bf55d36a69","arbitralCourtId":1,"nickName":"徐洋","applicantName":"赵春","arbitralCourtName":"第一仲裁庭","times":1,"caseNumber":"常钟劳人仲案字〔2023〕第26号","scheduleDate":"2023-05-24T00:00:00","caseName":"劳动报酬","respondentName":"赵夏","startTime":"08:30:00","id":23,"endTime":"08:45:00","status":"3"},{"caseCode":"e3a68febb9294112a85dfeffc00002d6","arbitralCourtId":1,"nickName":"周圆","applicantName":"申请人加密","arbitralCourtName":"第一仲裁庭","respondentCompanyName":"被申请单位加密","times":3,"caseNumber":"常钟劳人仲案字〔2023〕第12号","scheduleDate":"2023-05-23T00:00:00","caseName":"测试加密1111","startTime":"18:30:00","id":22,"endTime":"18:45:00","status":"3"},{"caseCode":"e3a68febb9294112a85dfeffc00002d6","arbitralCourtId":1,"nickName":"周圆","applicantName":"申请人加密","arbitralCourtName":"第一仲裁庭","respondentCompanyName":"被申请单位加密","times":2,"caseNumber":"常钟劳人仲案字〔2023〕第12号","scheduleDate":"2023-05-19T00:00:00","caseName":"测试加密1111","startTime":"08:45:00","id":21,"endTime":"09:15:00","status":"2"},{"caseCode":"9ae48862deaa4c24982b8bef5993d00d","arbitralCourtId":1,"nickName":"徐洋","applicantName":"数据库加密申请人1,申请人2","arbitralCourtName":"第一仲裁庭","respondentCompanyName":"数据库加密单位","times":1,"caseNumber":"常钟劳人仲案字〔2023〕第11号","scheduleDate":"2023-05-12T00:00:00","caseName":"加密测试案件","startTime":"09:00:00","id":19,"endTime":"09:30:00","status":"1"},{"caseCode":"e3a68febb9294112a85dfeffc00002d6","arbitralCourtId":1,"nickName":"周圆","applicantName":"申请人加密","arbitralCourtName":"第一仲裁庭","respondentCompanyName":"被申请单位加密","times":1,"caseNumber":"常钟劳人仲案字〔2023〕第12号","scheduleDate":"2023-05-12T00:00:00","caseName":"测试加密1111","startTime":"12:30:00","id":20,"endTime":"15:00:00","status":"1"},{"caseCode":"73c606f4dfca4137b3c0f4ee6ed4b9f9","institutionId":2,"arbitralCourtId":1,"nickName":"姜哲","deptId":102,"arbitralCourtName":"第一仲裁庭","times":1,"caseNumber":"常钟劳人仲案字〔2023〕第3号","scheduleDate":"2023-05-05T00:00:00","caseName":"赔偿医疗费","startTime":"08:30:00","id":18,"endTime":"08:45:00","status":"3"},{"caseCode":"793855c4cab545099752d7b4dd2ef402","times":1,"arbitralCourtId":1,"caseNumber":"常钟劳人仲案字〔2023〕第10号","nickName":"刘祥任","scheduleDate":"2023-05-04T00:00:00","caseName":"某某公司拖欠工资","startTime":"09:00:00","id":16,"endTime":"09:30:00","arbitralCourtName":"第一仲裁庭","status":"1"}],"code":200,"msg":"查询成功"}',
},
height: {
type: String,
default: "100%",
},
width: {
type: String,
default: "100%",
},
checkId: {
type: String,
default: "",
},
isEdit: {
type: Boolean,
},
},
methods: {
/**
* @description 初始化JSON数据,将其变成AST树;
*/
initJSON() {
// console.log(this.json)
if (!this.json) return;
let jsonObj = JSON.parse(this.json);
this.JsonAST = {
label: "",
type: "Object",
_id: "0",
isExpand: true,
children: this.JsonRecursionToAst(jsonObj, "0"),
};
},
/**
* @description 递归处理JSON数据,返回AST树;
*/
JsonRecursionToAst(jsonVal, _parentId, _parentKey) {
let _type = this.getType(jsonVal);
let currentArr = [];
// 通过传入类型决策使用
let _typeDecision = {
Array: () => {
if (jsonVal.length != 0) {
jsonVal.forEach((item, idx) => {
let current = {
label: String(idx),
_id: `${_parentId}-${idx}`,
type: this.getType(item),
_key: `${_parentKey}[${idx}]`,
};
if (current.type == "Object" || current.type == "Array") {
current.isExpand = true;
current.children = this.JsonRecursionToAst(
item,
current._id,
current._key
);
}
currentArr.push(current);
});
}
return currentArr;
},
Object: () => {
let currentKeys = Object.keys(jsonVal);
if (currentKeys.length != 0) {
currentKeys.forEach((key, idx) => {
let current = {
label: key,
_id: `${_parentId}-${idx}`,
type: this.getType(jsonVal[key]),
_key: `${_parentKey ? _parentKey + "." : ""}${key}`,
};
if (current.type == "Object" || current.type == "Array") {
current.isExpand = true;
current.children = this.JsonRecursionToAst(
jsonVal[key],
current._id,
current._key
);
}
currentArr.push(current);
});
}
return currentArr;
},
};
return _typeDecision[_type]();
},

/**
* @description 将AST语法树转换为显示List
*/
AstRecursionToList(AstTree) {
let list = [];
let _type = this.getType(AstTree);
let _typeDecision = {
Array: () => {
AstTree.forEach((_node) => {
const { label, type, _id, _key } = _node;
if (type == "Array" || type == "Object") {
const { isExpand, children } = _node;
if (isExpand) {
const chileList = this.AstRecursionToList(children) ?? [];
chileList.unshift({
label,
type,
_id,
isExpand,
_key,
});
chileList.push({
endTag: true,
_id,
type,
});
list = list.concat(chileList);
} else {
list.push({ label, type, _id, isExpand, children, _key });
}
} else {
list.push({ label, type, _id, _key });
}
});
return list;
},
Object: () => {
const { label, type, _id, _key } = AstTree;
if (type == "Array" || type == "Object") {
const { isExpand, children } = AstTree;
// 如果展开标志位为true,则继续递归,否则不进行递归
if (isExpand) {
const chileList = this.AstRecursionToList(children) ?? [];
chileList.unshift({
label,
type,
_id,
isExpand,
_key,
});
chileList.push({
endTag: true,
type,

_id,
});
list = list.concat(chileList);
} else {
list.push({ label, type, _id, isExpand, _key });
}
} else {
list.push({ label, type, _id, _key });
}
return list;
},
};
return _typeDecision[_type] && _typeDecision[_type]();
},
/**
* @descripotion 修改AST语法树中isExpand状态
*/
changeIsExpandInAst(tree, id) {
let _type = this.getType(tree);
let _typeDecision = {
Array: () => {
tree.forEach((node) => {
const { type, _id } = node;
if (_id == id) {
node.isExpand = !node.isExpand;
return;
}
// 如果当前层级拥有子级,并且id前缀可以匹配,则进行递归
if (
(type == "Object" || type == "Array") &&
Object.hasOwnProperty.call(node, "children") &&
id.indexOf(_id) > -1
) {
this.changeIsExpandInAst(node.children, id);
}
});
},
Object: () => {
const { _id } = tree;
// 如果匹配,则直接修改状态并返回
if (_id == id) {
tree.isExpand = !tree.isExpand;
return;
}
// 如果当前层级拥有子级,并且id前缀可以匹配,则进行递归
if (Object.hasOwnProperty.call(tree, "children") && id.indexOf(_id) > -1) {
this.changeIsExpandInAst(tree.children, id);
}
},
};
_typeDecision[_type]();
},
/**
* @description 获取数据类型
*/
getType(val) {
const type = Object.prototype.toString
.call(val)
.replace("[object ", "")
.replace("]", "");
return type == "Null" ? "String" : type;
},
/**
* @description 获取缩进长度,默认靠左多2em
*/
getIndentation(id) {
return id?.split("-")?.length * 2 ?? 2;
},
getCheckStatus(id) {
const flag = this.checkBoxList.filter((checkBox) => checkBox == id).length != 0;
if (flag) {
return true;
} else {
return false;
}
},
checkChange(e, id, key, label) {
if (Array.from(id).length == 0) return;
this.checkBoxKey += 1;
if (e) {
if (this.checkBoxList.length == 0 || this.checkBoxList.length == 1) {
this.checkBoxList = this.createIdsFromNodeId(id);
} else {
// 设置是否允许修改标志位
let canEdit = true;
let checkList = this.createIdsFromNodeId(id);
if (checkList.length < this.checkBoxList.length) {
this.$message.warning("请先取消已选中的同级字段,在进行勾选");
return;
}
for (let index = 0; index < this.checkBoxList.length - 1; index++) {
const element = this.checkBoxList[index];
if (element != checkList[index]) {
canEdit = false;
}
}
if (canEdit) {
this.checkBoxList = checkList;
} else {
this.$message.warning("请先取消已选中的同级字段,在进行勾选");
}
}
} else {
let canEdit = this.checkBoxList.filter((box) => box == id).length != 0;
if (canEdit) {
let checkBoxList = this.createIdsFromNodeId(id);
checkBoxList.pop();
this.checkBoxList = checkBoxList;
} else {
this.$message.warning("请先取消已选中的同级字段,在进行勾选");
}
}
const c_id = this.checkBoxList?.slice(-1)[0];
c_id == this.checkId ? "" : this.getKeyAndId(c_id);
},
//返回path id
getKeyAndId(id) {
const obj = this.LiList.find((item) => item._id == id);
obj ? this.$emit("change", { path: obj._key, id: obj._id }) : "";
},
/**
* @description 根据id生成数组
*/
createIdsFromNodeId(id) {
let list = [];
id.split("-").forEach((item) => {
if (list.length == 0) {
list.push(item);
} else {
list.push(`${list[list.length - 1]}-${item}`);
}
});
return list;
},
/**
* 预览模式设置选中元素
*/
setcheckId() {
const { checkId } = this;
this.checkChange(true, checkId ?? "");
},
},
watch: {
checkId(e) {
console.log(e);
},
json: {
handler(val) {
if (typeof val == "string") {
this.initJSON();
} else {
// 如果传入的值不为JSON格式,抛异常
console.error("inputDataType not JSON!");
}
},
immediate: true,
deep: true,
},
JsonAST: {
handler(val) {
this.LiList = this.AstRecursionToList(val);
this.$nextTick(() => {
this.setcheckId();
});
},
immediate: true,
deep: true,
},
},
render() {
// 单独生成一行html
let singLineHtml = (_node) => {
// const {label, type, _id} = _node;
return (
<div style={{ textIndent: `${this.getIndentation(_node._id)}em` }}>
{createLabel(_node)}
{createTypeTag(_node)}
{createExpandTag(_node)}
{createBracket(_node)}
{createCheckBox(_node)}
</div>
);
};
let createLabel = (_node) => {
if (Object.hasOwnProperty.call(_node, "label") && _node.label?.length != 0) {
return <span>{`"${_node.label}":`}</span>;
}
};
let createExpandTag = (_node) => {
if (Object.hasOwnProperty.call(_node, "isExpand")) {
const { isExpand, _id } = _node;
return (
<i
onClick={() => {
this.changeIsExpandInAst(this.JsonAST, _id);
}}
style="color:#ff9a00;"
class={
isExpand
? "el-icon-remove-outline expandTag"
: "el-icon-circle-plus-outline expandTag"
}
></i>
);
}
};
let createTypeTag = (_node) => {
if (!Object.hasOwnProperty.call(_node, "endTag")) {
const { type } = _node;
return <span class={`tag ${type}-tag`}>{type}</span>;
}
};
let createBracket = (_node) => {
const { type } = _node;
if (Object.hasOwnProperty.call(_node, "endTag")) {
if (type == "Array") {
return (
<span>
<span class="bracket-array">{"]"}</span>,
</span>
);
} else {
return (
<span>
<span class="bracket-object">{"}"}</span>,
</span>
);
}
} else if (Object.hasOwnProperty.call(_node, "isExpand")) {
const { isExpand } = _node;
// 展开
let expandStrategy = {
Array: () => {
return (
<span>
<span class="bracket-array">{"["}</span>
</span>
);
},
Object: () => {
return (
<span>
<span class="bracket-object">{"{"}</span>
</span>
);
},
};
// 关闭
let notExpandStrategy = {
Array: () => {
return (
<span>
<span class="bracket-array">{`[${_node.children.length}]`}</span>,
</span>
);
},
Object: () => {
return (
<span>
<span class="bracket-object">{"{...}"}</span>,
</span>
);
},
};
return isExpand ? expandStrategy[type]() : notExpandStrategy[type]();
} else {
return <span>,</span>;
}
};
let createCheckBox = (_node) => {
if (!Object.hasOwnProperty.call(_node, "endTag")) {
const { _id, _key, label } = _node;
return (
<el-checkbox
key={this.checkBoxKey}
style={this.isEdit ? "pointer-events:none" : ""}
value={this.getCheckStatus(_id)}
onChange={(e) => {
this.checkChange(e, _id, _key, label);
}}
></el-checkbox>
);
}
};
return (
<ul
class="json-container"
style={{ height: this.height, width: this.width }}
ref="JsonContainer"
>
<div class="json-index"></div>
{this.LiList.map((node, idx) => {
return (
<li>
<span class="line-head">{idx + 1}</span>
{singLineHtml(node)}
</li>
);
})}
</ul>
);
},
};
</script>

<style lang="scss" scoped>
.json-container {
background-color: #fff;
overflow: auto;
color: #767676;
position: relative;
.json-index {
width: 44px;
height: 100%;
background: #f5f5f5;
position: absolute;
top: 0;
left: 0;
// border-right:1px solid #E7E7E7;
}
li {
height: 35px;
line-height: 35px;
display: flex;
font-size: 14px;
position: relative;
.line-head {
display: inline-block;
height: 35px;
line-height: 35px;
width: 44px;
box-sizing: border-box;
font-size: 14px;
text-align: center;
border: solid #e7e7e7;
border-width: 0 1px 1px 0;
background: #f5f5f5;
// &:last-of-type{
// border-width: 0 1px 0px 0;
// }
}
}
}
.tag {
box-sizing: border-box;
padding: 3px 7px;
display: initial;
border-radius: 4px;
margin-left: 2px;
margin-right: 2px;
color: #fff;
background-color: #c9c9c9;
font-size: 12px;
}
.Object-tag {
background-color: #ff9a00;
}
.Number-tag {
background-color: #2b7cf5;
}
.String-tag {
background-color: #00a870;
}
.Array-tag {
background-color: #a17bd1;
}
.bracket-object {
color: #ff9a00;
}
.bracket-array {
color: #a17bd1;
}
.expandTag {
cursor: pointer;
display: initial !important;
}
::v-deep.el-checkbox {
display: initial;
.el-checkbox__input {
display: initial;
}
// .el-checkbox__input.is-disabled.is-checkId .el-checkbox__inner{
// background: #2B7CF5;
// &::after{
// border-color: #FFF;
// }
// }
}
</style>


思维导图


微信截图_20240415152236.png


主要函数解读


JsonRecursionToAst


这个方法是递归处理传入的JSON数据,首先通过getType方法获取当前节点的数据类型【getType中通过原型链方式获取数据类型】,根据数据类型决策返回数据【主要节点参数是label(key),_id(节点ID),type(节点数据类型),其余的参数为业务需求】;


AstRecursionToList


直接通过AST树去生成DOM结构的话我觉得会比较复杂,所以我就在AST树与DOM结构之间写了此方法,这个方法去监听AST树,只要树发生了变化便会执行次方法;首先进入这个方法后根据节点类型去决策进入哪个结构,然后根据isExpand判断是否展开,若不展开则直接不向下执行,若展开,则继续递归;


changeIsExpandInAst


此方法是修改展开状态的,通过_id进行匹配,只要前缀相同,则递归,直至完全相同修改状态;


checkChange


这个方法是业务逻辑的需求,可以点击节点前的复选框,但是不允许点击不同分支的复选框;


作者:用户352970449145
来源:juejin.cn/post/7357698682744143911
收起阅读 »

从字节到小县城做三份远程工作,区块链技术给我带来了什么?

2022年,我决定离开字节跳动,这一决定标志着我职业生涯的一次重大转变。我转向了区块链行业,开始了远程工作和数字游民生活。我的经历不仅是个人转型的故事,更是关于程序员如何借助区块链赛道的发展机会,摆脱国内互联网的过度内卷,像我一样成长为数字游民。 结合我自己的...
继续阅读 »

2022年,我决定离开字节跳动,这一决定标志着我职业生涯的一次重大转变。我转向了区块链行业,开始了远程工作和数字游民生活。我的经历不仅是个人转型的故事,更是关于程序员如何借助区块链赛道的发展机会,摆脱国内互联网的过度内卷,像我一样成长为数字游民。


结合我自己的经历,给大家分享的是作为程序员,如何从传统互联网行业到区块链行业的转型,特别是针对想要从事远程工作的开发同学分享一些我的思考和路线建议。



(边旅行边远程)


区块链是什么?


区块链技术自2008年比特币的问世以来,已经展示了其在多个领域的应用潜力,包括金融、供应链、医疗和艺术等。到今天,区块链不仅限于加密货币,智能合约和去中心化应用(DApps)已经成为推动技术前进的新动力。


为什么在区块链领域,一定要看海外的发展机遇?


在国外,特别是在欧美,区块链技术得到了飞速发展。例如,美国、瑞士和新加坡等国家已经制定友好的区块链政策,吸引了大量的区块链创业公司和投资。海外的区块链开发通常能享受到更加宽松的监管环境和更多的资金支持,这些因素共同促成了一个成熟的区块链生态系统。


在我们国家,大多数区块链企业会选择在香港。对于我们来说,如果短时间英文口语不太能提升,可以多关注香港、新加坡的远程机会。企业和项目还是非常多。



(在安吉DNA)


学习区块链是选老牌公链还是新链?


区分老牌公链和新链是入门并理解区块链的关键。


老牌公链如比特币和以太坊,已经建立了坚实的基础,拥有庞大的用户和开发者社群。新链,如Solana和Polkadot,虽然起步较晚,但在技术创新(例如更快的交易处理速度和更低的手续费)和特定应用场景上可能有更具吸引力的优势。


对于开发而言,选择专注于老牌公链还是新链,应根据个人的兴趣和市场需求来决定:



  • 老牌公链开发:更适合那些喜欢稳定、渐进式创新和长期投资的开发同学。

  • 新链开发:适合追求技术创新边界,愿意在新兴技术上投入时间和精力的开发者。


作为区块链的从业者,我建议新手还是先学一下老牌公链技术,对你后续的发展更有利,也相对更容易转型。


不同技术栈如何转型区块链


对于希望从传统技术栈转型至区块链开发的程序员,每个技术栈的转型路径都会有所不同。我给大家列了一个详细的指南,包括推荐的步骤、大概所需的时间周期以及可能的目标岗位。这样的规划旨在为有志于区块链领域的开发者提供清晰的职业发展路径。



(远程公司寄来的礼物)


一、区块链转型指南


我用一张表详细描述了从不同web2技术栈转型至区块链开发的具体步骤、周期和目标岗位:


3.png



  • 智能合约 开发:对于绝大多数开发同学来说,转型区块链开发,建议先学区块链技术原理集合智能合约,就业方向是智能合约开发。

  • 区块链前/后端开发:如果具备web经验,比如前端、后端Go/Node/Java等,建议转区块链后端开发。



    • Java的解决方案:Java技术栈同学可以先用Java技术栈拆解区块链项目,然后直接去求职。工作中再切换语言。语言难度并不大。

    • 对于前端同学,如果原本不具备后端 Node 能力,那就学 DApp 前端,也够用。



  • 相对转型周期更长的技术栈:C#、Android、iOS、Php、Python大数据、算法、运维开发等。



    • 直接转智能合约也可以,但是建议可以先补充点 web 开发能力,这样更好就业,这件事也可以通过我们训练营的资源。

    • 其次,你同时学习区块链基础课程和任务,包括智能合约相关课程并不冲突。只是在第六周之后的项目实战阶段,会比较依赖你的web开发能力,否则项目任务没办法完成。




二、转型步骤解析


Step1 学习 区块链技术 原理,建立认知

对所有技术栈的开发同学来说,第一步都是建立区块链技术的基础知识,理解其工作原理、主要特性以及实际应用场景。


Step2 技术深入和框架学习

不同的技术栈应侧重于学习与其专业相关的区块链技术。例如,Java开发可以专注于区块链后端开发,最好掌握主流区块链框架,而前端开发则应学习如何通过Web3.js等库与区块链交互。


Step3 项目实战

理论学习后,参与实际项目是检验和加深技术理解的最好方式。实战经验不仅能帮助巩固学习成果,也是提高市场竞争力的关键,帮助求做好铺垫



(在数字游民公社)


远程工作带来的机遇


远程工作为程序员提供了前所未有的自由度。我在小县城通过远程工作不仅实现了生活和工作的平衡,还能参与到全球项目中。


远程也带来了挑战,尤其是在沟通和协作方面。对于非英语母语的开发同学,提升英语能力是关键,这包括进行模拟面试、加强专业术语的使用,以及在实际工作中不断实践英语沟通。


建立远程工作社群


基于我这些年的经验,以及我曾经合作过的身边大厂同学转型的案例。我们正在建立一个远程工作社群,这不仅是一个远程工作技术交流的平台,更是相互支持和资源共享的社区。


我们希望通过这个社群帮助更多开发者顺利过渡到区块链领域,尤其是那些对远程工作感兴趣的朋友们。


最后要说的话


转型的道路充满了不确定性和挑战,但也充满了机遇。从字节跳动辞职,到在小县城同时做三份远程工作,我的经历或许能给正在考虑转型的你一些启示和勇气。


区块链不仅是技术的革新,更是职业生涯的一个新起点。如果你对区块链感兴趣,或许现在是跨入这个领域的最好时机。



作者:C2N数字游民部落
来源:juejin.cn/post/7356326955929075712
收起阅读 »

哭了,朋友当韭菜被割惨了

最近我的朋友,被某些知识付费坑得很惨。全程毫无干货可言。内容仅仅只适用于初级、或者说部分中级的程序员。为此,我的朋友交了大几千的学费,却收获甚微。 当然,你可能说,是你的朋友问题啊?你朋友烂泥扶不上墙,学习方法不对,别人都有很多成功的案例。什么offer收到...
继续阅读 »

最近我的朋友,被某些知识付费坑得很惨。全程毫无干货可言。内容仅仅只适用于初级、或者说部分中级的程序员。为此,我的朋友交了大几千的学费,却收获甚微。



当然,你可能说,是你的朋友问题啊?你朋友烂泥扶不上墙,学习方法不对,别人都有很多成功的案例。什么offer收到手酸,外包入大厂。




我买这些课就是为了学习,入门一些语言。知识付费很合理呀!!



于是我跟我朋友在微信彻夜长谈,有了如下分析


先说结论



请擦亮你的慧眼,你的一分一毫来之不易。不到迫不得已,才当学费



为什么这么说?


首先,不管你是想就业,还是想学习一些新的技术,网上都有例子,github上也会有前沿的项目提供学习。


类型结论
学习新技术某项技术开源出来,作为技术的布道者,恨不得你免费过去学习,然后你再发一篇文章,越来越多人学习你的技术。
就业简历包装无非就是抄抄抄,抄别人的优秀代码。github开源项目就非常合适

其次,你学费,一定要做到利益最大化。必须要有以下两点



  • 能学到大部分人都学不到的技术亮点。记住,是大部分人,一定要做到差异化

  • 能学到优秀的学习方法,push你前进。


开启慧眼


现在市面的学习机构,鱼龙混杂。,B站大学,某识xin球,某ke时jian 甚至,在某音上,都有那种连麦做模拟面试,然后引导你付费学习。


就业环境不好,买方市场竞争激烈,某些人就抓住你的焦虑心理,坑你一把。回想你的求学生涯,是否也有类似被坑经历?醒醒吧,少年。能救你的,只有你自己


当然,小海也会有潜龙。不可否认,知识付费为我们提供了便利性。



  • 原本散乱无章的知识点,人家给你整理好了,你尽管就是学习,实践

  • 面对焦虑,你觉得很迷茫,需要一个人指点你前进

  • 能认识更多同样诉求的人,为以后学习,就业,甚至做生意提供可能


但是,某些不法分子,就是抓住你的这个心理,疯狂ge你韭菜。什么10块钱知识手册,19.9面试题,100块钱的项目视频。天天一大早,就转发一些公众号到你群上,dddd。


这些内容,不是说没有用。我们讨论适合人群,这类东西不适合中高级程序员



说那么多,你得学会判断这个人是不是大佬




你都可以简历包装,为什么‘大佬’就不会是被包装的



那就稍微整理一下,哪些是真大佬,伪大佬


真伪大佬


某佬博客开源项目学习人群是否顺眼
伪大佬面试题居多,很多基础内容,没有干货无,或者很少。动不动就是商城,博客应届生占比较多可能顺眼
真大佬博客、论坛内容干货。整理分类完善,你能学到东西有,某些大项目的贡献,同时也有优秀开源项目应届生,中高级都有大多数不顺眼,因为实在优秀

就学习人群做一个说明



  • 在就业容易程度上,相对于初中高级别的程序员,应届生无论从考察的内容,招聘的人数。都会容易丢丢。

  • 他说跟着他学,offer赢麻了。但是其中,找到工作的大多数都是应届生


就这些点,我们其实可以能判断个大概了。


记住,你想知识付费。一定要摸清他的底细,不能认为他说得都是对的。人家也是会包装的


你的hello world


或许每个程序员的第一行代码,都是


    print("hello world")

我想说的是,请你记住你的初心。



  • 转行过来当程序员,就是为了狠狠赚他一笔

  • 喜欢写代码,苦中作乐


情况每个人都不太一样,这里不细说。明白你是谁,你还是否有动力能坚持下去。明白这一点,远比你在迷茫的时候病急乱投医更为重要,请勿过度焦虑


为此,后面会说一下如何学习,以及找工作如何不被骗


力量大会


事关钱包的问题,我们都得谨慎谨慎。就业市场那恶劣,朋友找不到工作还被坑了一把。骗子实在可恶。请你先自身强大,先自己找出问题,不花冤枉钱,避免传销式编程


如有雷同,纯属巧合,没有针对任何人,也没有动某些人的饭碗。


作者:Goland猫
来源:juejin.cn/post/7357231056288055336
收起阅读 »

24清明节咋过的?

头一天在朋友家呆了一天,下午又去武汉最负盛名的公园溜达了一会。 晚上回家,打算出去骑车,一直没想到目的地,想去大山里,但是总感觉自己的行李不顺心,帐篷太长,也没有炊具,没有视频里up主们那种风餐露宿,悠然自得的感觉。 这估计就是典型的i人了。只要有一点不顺遂...
继续阅读 »

头一天在朋友家呆了一天,下午又去武汉最负盛名的公园溜达了一会。


东湖.jpg
晚上回家,打算出去骑车,一直没想到目的地,想去大山里,但是总感觉自己的行李不顺心,帐篷太长,也没有炊具,没有视频里up主们那种风餐露宿,悠然自得的感觉。


这估计就是典型的i人了。只要有一点不顺遂,就会变的犹犹豫豫,然后大概率放弃。


然后我就放弃了原本打算去大山里待两天的计划。当然,我还是朝着大山所在的方向出发了。


打开地图,切换到地形模式,就可以看到藏在平面图里的山川河流了,我发现了一条沿着长江边伸展出去的小路,于是把这条路当做了我的目的地。


应该的假期的缘故,早上出发的时候难得的没有遇到堵车,很多路我都没有开导航,全凭感觉在走。有时候看到有趣的小路我还会直接拐进去。


有一回我拐到了一个小山下面,上山的小路就在眼前,但是因为前几天下雨的缘故,路上还有积水和泥泞的车辙印,休闲骑不越野,遂放弃上山。


后来又经过一个小镇,就跟着前面一辆小电动车一起穿街走巷,最后到路的尽头,发现正是长江,而我也终于拐到了那条沿江的小路上。这条路同时是长江的防洪堤,路边每隔几百米就有一块牌子,提醒过路的人们防洪的重要性。


我沿着江堤一直走啊走,左边是缓慢流淌的长江,右边是无边无际的田野。往左边看,是孤帆远影碧空尽,往右边看又是莽莽沃野,风吹草低。


微信图片_20240409134731.jpg
骑了大约半个小时左右,感觉有点尿急了,可是在江堤上,找个厕所是不可能了,但是也不能随地就解决啊,路上时常还有车辆经过。


又骑了一会看到了一个破房子,就在路边不远处,掩在杂草丛中,心想这里算是比较隐蔽的了,下车走过去。可是越靠近那破房子就越觉得恐惧,脑子里开始蹦出来一些恐怖片的情景。其实我是不怕鬼怪的,咱是一个坚定的唯物主义者,当然我也不怕活人。但是我怕尸体,动物的就算了,这万一。


这还要从大学那会说起,学校后面有座小山,山上有几座破房子,那时候大家经常爬山去上面看日落日出,我也去过几次,对那个房子也算记忆深刻。后来有一天学校突然开始统计人数,一个一个的查,态度之庄重坚决,行动之迅速果断,前所未见。最后才得知原来有学生在后山的破房子里发现有人上吊了,这事给我留下了极大的阴影。以至于后来我都不敢去那座山上了。


言归正传,我还是壮着胆子靠近了这座破房子,这是一座典型的南方小楼,好像是两层,门洞很窄,门窗都没有了,一楼很干净,有一条狭窄的楼梯可以通到二楼。我也就到此为止了。当然我也不敢在这上厕所了。


又骑了一会,油灯开始闪烁了,上周加了50块钱的油,当时就跑了大约180公里,今天又跑了大约60公里,一合计50块钱的油跑了240公里,心里又快乐了,比之前50块钱跑200公里的时候还快乐。经过半年的磨合,我和车子终于要人车合一了。


打开地图搜索了一个最近的加油站,十几公里,又加了50块钱的油。冬天的时候一个月就加一次油,春天了基本两周就要加一次,这么一想我又不快乐了。


加完油已经到饭点了,果然人车合一了,要饿一起饿。在小镇上点了一份炒菜,一个人吃就点了一份鱼香肉丝,分量还挺足的,竹笋很脆嫩,现在是吃春笋的时节。


微信图片_20240409134748.jpg
吃完饭,又开始漫无目的的骑车,没有开导航,只是这次长江在我的左手边,因为小镇所在的位置是长江转弯处突出的一块洼地上,所以我以为我正在沿小镇绕圈,也可能是一路上的风景同质化太严重了,以至于我一直没发现正在走回头路。


然后就在我又一次尿急,开始搜寻合适的放水地的时候,我又看到了那座老房子。


作者:渡人先渡己
来源:juejin.cn/post/7355433339547664403
收起阅读 »

降本增笑,领导要求程序员半年做出一个金蝶

关于降本增效的事,今天在网上看到一个帖子,虽然有点搞笑,但是对于打工人(特别是技术同学)来说,可挖掘的东西也不少,特别分享给大家。 真的是好多年没听说这样的事了,记得以前总有老板让做个淘宝、做个京东,然后预算只有几千块,最多几万块。 这些故事程序员谈起来往往...
继续阅读 »

关于降本增效的事,今天在网上看到一个帖子,虽然有点搞笑,但是对于打工人(特别是技术同学)来说,可挖掘的东西也不少,特别分享给大家。



真的是好多年没听说这样的事了,记得以前总有老板让做个淘宝、做个京东,然后预算只有几千块,最多几万块。


这些故事程序员谈起来往往都是哈哈一笑,并疯狂吐槽一番。



不过笑过之后,大家是否想过如何去解决问题?或者真的去评估下可行性,探索一下可能的实现路径。


找到问题


首先我们看下老板的问题。老板的根本问题并不是想要做金蝶,为什么这么说呢?


我们看看网友的描述就知道了:经济下行,领导不想出金蝶系统的维护费,不想为新功能花大价钱。这才是根本问题,用四个字来说就是:降低成本。


然后才是老板想到能不能用更少的钱达到金蝶系统的使用效果,再之后才是自己能不能做一个类似金蝶的系统,并思考了自己可以承担的成本:一个前端、一个后端,半年时间。


最后问题被抛到了这位网友的手里。可以看得出来这位网友也不太懂,还去咨询了朋友。不知道它有没有向朋友说清楚问题,还是只说了老板想自己做一个金蝶系统,结果是朋友们都说不可行。


遇到问题时,我们得把这个问题完完整整的捋一遍,找到最根本的问题,然后再说怎么解决问题,否则只是停留在表面,就可能事倍功半。在这个上下文中,根本的问题就是:降低成本。



解决问题


明确了老板的根本问题,我们就可以琢磨方案了。既然是降低财务系统的成本,可行的方案应该还是有几个的。


使用替代产品


假如公司只使用产品的部分功能,是不是可以选择金蝶的低版本?是不是可以降低一些人头费?


金蝶的服务贵,是不是可以选择一些小厂的产品?国内做财务系统的应该挺多的,小厂也更容易妥协。


或者选择SaaS服务,虽然SaaS用久了成本也不低,但是可以先撑过这几年,降低当前的支出。


当然替换财务系统也是有成本的,需要仔细评估。不过既然都想自己做了,这个成本应该能hold住。


找第三方维护


金蝶的服务贵,是不是可以找其它三方或者个人来维护修改?根据我之前的了解,金蝶这种公司有很多的实施工作是外包出去的,或者通过代理商来为客户服务,能不能找这些服务商来代替金蝶呢?或者去某些副业平台上应该也能找到熟悉金蝶系统的人。


当然这个还要看系统能不能顺利交接,金蝶有没有什么软硬件限制,第三方能不能接过来。


另外最重要的必须考虑系统和数据的安全性,不能因小失大。


自己开发


虽然自己开发的困难和成本都很高,但我仍旧认为这可能也是一个合适的解决方案。理由有下面两点。



  • 功能简单:如果公司的业务比较简单,使用的流程也简单,比如不使用涉及复杂的财务处理,那么捋一捋,能给开发人员讲清楚,也是有可能在短时间内完成的。

  • 迭代渐进:长城不是一天建成的,系统也都是逐渐迭代完善的。自己开发可以先从部分模块或者功能开始,然后逐步替换,比如前边的流程先在新系统中做,最后再导入金蝶。即使不能做到逐步替换,也可以控制系统的风险,发现搞不定时,及时止损。相信老板也能明白这个道理,如果不明白或者不接受,那确实搞不了。



当然我们也肯定不能忽视这其中的困难。我之前做过和金蝶系统的对接,订单的收付款在业务系统完成,然后业务系统生成凭证导入到金蝶K3。依稀记得业务也不算复杂,但是需求分析做了好几遍,我的代码也是改了又改,上线之后遇到各种问题,继续改,最终花了几个月才稳定下来。


事后分析原因,大概有这么几点:



  • 产品或者需求分析人员没接触过类似的业务,即使他对财务系统有一些经验,也不能准确的将客户的业务处理方式转换到产品设计中;

  • 财务人员说不明白,虽然他会使用金蝶系统,但是他不能一次性的把所有规则都讲出来,讲出来也很难让程序员在短时间内理解;

  • 程序员没做过财务系统,没接触过类似的业务,系统的设计可能要反复调整,比如业务模块的划分逻辑,金额用Long还是用BigDecimal,数据保留几位小数,这都会大幅延长开发周期,如果不及时调整就可能写成一锅粥,后期维护更困难。


这还只是和金蝶系统做一个简单的对接,如果要替代它,还要实现更多的功能,总结下,企业可能会面对下面这些困难:


业务复杂:财务规则一般都比较复杂,涉及到各种运算,各种数字、报表能把人搞晕。如果公司的业务也很复杂,比如有很多分支或者特殊情况,软件开发的难度也会很大,这种难度的变化不是线性增加的,很可能是指数级增长的,一个工作流的设计可能就把人搞死了。


懂业务的人:系统过于复杂时,可能没有一个人能把系统前前后后、左左右右的整明白。而要完成这样一个复杂的系统,必须有人能从高层次的抽象,到具体数字运算的细枝末节,完完全全的整理出来,逻辑自洽,不重不漏,并形成文档,还要能把程序员讲明白。


懂架构的人:这里说的是要有一个经验丰富的程序员,不能是普通的码农,最好是有财务系统开发经验的架构师。没走过的路,总是要踩坑的。有经验的开发人员可以少走很多弯路,极大降低系统的风险。这样的人才如果公司没有,外招的难度比较大,即使能找到,成本也不低。


灵活性问题:开发固定业务流程的系统一般不会太考虑灵活性的问题,如果业务需要调整,可能需要对系统进行大幅修改,甚至推倒重来。如果要让系统灵活些,必然对业务和技术人员都提出了更高的要求,也代表着更强的工作能力和更多的工作量。


和其它系统的对接:要不要和税务系统对接?要不要和客户管理系统对接?要不要和公司的OA对接?每一次对接都要反复调试,工作量肯定下不来。


总之,稍微涉及到财务处理的系统,都不是一个前端和一个后端能在短时间内完全搞出来的。


对程序开发的启示


搞清楚需求


日常开发过程中,大家应该都遇到过不少此类问题。领导说这里要加个功能,然后产品和开发就去吭哧吭哧做了,做完了给领导一看,不是想要的,然后返工反复修改。或者说用户提了一个需求,产品感觉自己懂了,然后就让开发这么做那样改,最后给用户一看,什么破玩意。这都是没有搞清楚真正的需求,没有触达那个根本问题。


虽然开发人员可以把这些问题全部甩给产品,自己只管实现,但这毕竟实实在在的消耗了程序员的时间,大量的时间成本和机会成本,去干点有意义的事情不好吗?所以为了不浪费时间,开发也要完整的了解用户需求。在一个团队中,至少影响产品落地的关键开发人员要搞懂用户的需求。


那么遇到这种问题,程序员是不是可以直接跑路呢?


也是一个选择, 不过对于一个有追求的程序员,肯定也是想把程序设计好、架构好的,能解决实际问题的,这也需要对用户需求的良好把控能力,比如我们要识别出哪些是系统的核心模块,哪些是可扩展能力,就像设计冯诺依曼计算机,你设计的时候会怎么处理CPU和输入输出设备之间的关系呢?


对于用户需求,产品想的是怎么从流程设计上去解决,开发需要考虑的是怎么从技术实现上去满足,两者相向而行,才能把系统做好。


当然准确把握用户的需求,很多时候并不是我说的这么容易,因为用户可能也说不清楚,我们可能需要不断的追问才能得到一些关键信息。比如这位网友去咨询朋友时,可能需求就变成了:我们要做一个财务系统,朋友如果不多问,也只能拿到这个需求,说不定这位朋友也有二次开发的能力,错失了一次挣钱的好机会。还有这位老板上边可能还有更大的老板,这位老板降低成本的需求也可能是想在大老板面前表现一下,那是不是还有其它降本增效的方法呢?比如简化流程、裁掉几个不关键的岗位(这个要得罪人了)。


我们要让程序始终保持在良好的状态,就要准确的把握用户需求,要搞懂用户需求,就需要保持谦逊求知的心态,充分理解用户的问题,这种能力不是朝夕之间就可以掌握的,是需要修炼的。


动起来


任何没有被满足的需求都是一次机会。


我经常会在技术社区看到一些同学分享自己业余时间做的独立产品,有做进销存的、客户管理的、在线客服的,还有解决问题的各种小工具,而且有的同学还挣到了钱。


我并不是想说让大家都去搞钱,而是说要善于发现问题、找到机会,然后动起来、去实践,实践的过程中我们可以发现更多的问题,然后持续解决问题,必然能让自己变得越来越强。在经济不太好的情况下,我们才有更强的生存能力。




啰里八嗦一大堆,希望能对你有所启发。




作者:萤火架构
来源:juejin.cn/post/7317704464999235593
收起阅读 »

腾讯云:颜面尽失的草台班子

昨天下午,2024年04月08日,腾讯云出现了一场全球性的大故障,用腾讯云官方的说法,崩了 74 分钟(15:31 - 16:45),波及全球 17 个区域与数十款服务。事实影响是什么但这与我观察到的事实不符 —— 从故障范围上来说,这次的故障几乎是去年阿里云...
继续阅读 »

昨天下午,2024年04月08日,腾讯云出现了一场全球性的大故障,用腾讯云官方的说法,崩了 74 分钟(15:31 - 16:45),波及全球 17 个区域与数十款服务。

事实影响是什么

但这与我观察到的事实不符 —— 从故障范围上来说,这次的故障几乎是去年阿里云双十一史诗级大故障的翻版 —— 小道消息是整个管控面 GG,云 API 挂了,所以现象与去年阿里云如出一辙:依赖云 API 的云产品控制台不能用了。

被管控的纯资源,如云服务器 CVM,云数据库 RDS, 设置了公开读写访问对象存储 COS 不受影响可以继续使用。然而依赖认证与API 的各种云 PaaS 服务,例如标准的私有读写的对象存储 COS,就抓瞎了。

因为阿里云至今没有做一个像样的事后故障复盘,因此在《我们能从阿里云史诗级故障中学到什么》中,我为阿里云的这次故障做了非官方的技术复盘。同样的判断逻辑完全也适用于这次故障 —— 这样的爆炸半径,根因出在 Auth 上的概率很大。目前,腾讯云仍然没有给出官方的事后故障复盘报告,也可能不会有了。


忽悠人的状态页

我的朋友杨攀曾写过一篇《中国云服务走向全球?先把 Status Page 搞定》,讨论了 Status Page (服务健康状态页)对于公有云服务的重要性,各家本土云厂商也跟进了这一特性,包括腾讯云。—— 状态页能在服务宕机的情况下有效减少客户的焦虑,降低沟通成本,但它的核心价值在于 “建立与客户的信任关系”。

看上去,腾讯云与阿里云的 Status Page 反应都比较迟缓,在故障发生后三四十分钟才开始更新。而不是像Cloudflare 等产品一样及时更新故障,或采用自动化方式监测到故障后立即推送。但不同于阿里云 —— 虽慢却诚实地标记了所有服务受到影响,腾讯云的 Status Page 连基本的真实性与准确性都堪称稀烂。

例如,受到影响的对象存储 COS 服务,在有用户上报问题的几个可用区中,我并没有看到 Status 标红。而这样的例子还有更多。事实上如果问题真出在管控 API 上,那么影响的范围应该和阿里云一样 —— 所有服务的控制面。因此,这样鸡贼的做法只会给客户留下:“不透明、有猫腻“ 的负面印象。


撒谎的三无公告

在故障出现 40 ~ 50 分钟后,腾讯云终于发出了第一份故障公告,也是截止到目前 Status Page 上唯一一份公告。但其内容就一句话 —— 三无公告:无时间(故障时间),无地点(可用区/AZ),无范围(影响服务)。而且姗姗来迟,比我替它发的公告《【腾讯】云计算史诗级二翻车来了》还晚了十分钟。

但这份公告最致命的问题是真实性与准确性:首先,故障绝对不仅仅是“控制台”,而是整个控制面。作为一个专业的云计算服务供应商,一字之差天壤之别,混淆两者区别的原因,要么是蠢(缺乏专业素养,台面混为一谈)。要么是坏(避重就轻,推卸责任)。

请问,一个全身休克的人,说他 “面色异常”,这是一个真诚的回复吗?请问,一台被砸烂的笔记本电脑,说它“敲击键盘没有反应”是一个有意义的描述吗?同理,一个控制面爆炸的公有云,说自己“控制台异常”,是一个认真的回复吗?

其次,从事后官微的发布与用户群的反馈来看,在这个时间,“目前故障已恢复”  是在撒谎。至少相当一部分服务的可用性事件是在 16:45 标记恢复的,在17 点前后,腾讯云产品吐槽群中也仍然有一些问题上报。

我认为这份对腾讯云带来的伤害远比服务宕机要大的多 —— 首先,在及时性,准确性上体现出了极差的专业素养。其次,在真实性上有意做手脚,会伤及公有云,或者说一切生意的根本 —— 诚信这对品牌形象是一个摧毁性打击。


灾难级别的公关


按理说,出现了这么严重的故障,应当用诚恳认真的态度去处理,但腾讯云官方微博居然还在抖机灵 —— 堪称灾难级别的公关水平

这条微博也再次扇了腾讯云自己官网公告的大嘴巴子 —— 16:45 分发第一条帖子时,“工程师仍在紧急修复中”,17:16,距离第一次报告故障的 15:31已经过去近两个小时,“已经整体恢复”。然而,根据腾讯云官网 16:21 发布的公告[1]声称:“故障已恢复”。从实际情况来看,再次证明了官网公告在说谎

阿里云双十一大故障的时候,刚刚开完云栖大会,打脸了吹下的极致高可用的牛逼,但毕竟隔了一周了。而腾讯云这次大故障的同时还在开发布会吹牛逼,还找特大号发了一篇软文:太意外了!国内80%大模型都存在鹅厂!》,发布时间 16:19,2分钟后官网发出故障通告,堪称光速打脸二次方

与之形成鲜明对照的是,去年 11 月 Cloudflare 的故障,Cloudflare CEO Matthew 亲自出来对故障进行道歉与复盘,相比之下,国内云厂商的危机公关堪称灾难级别 —— 彻底做实了草台班子的称号。

实锤的草台班子

请允许我引用瑞典马工的一句名言 :“阿里云是个工程质量差劲的正经云,但腾讯云是一群业余销售加业务码农玩游戏”。所谓光鲜亮丽的大厂,在里面也不过是一个又一个的草台班子。

Reference

公告: https://cloud.tencent.com/announce/detail/1995

https://www.oschina.net/news/286685

https://www.v2ex.com/t/1030638

https://www.v2ex.com/t/103061


云计算泥石流
曾几何时,“上云“近乎成为技术圈的政治正确,整整一代应用开发者的视野被云遮蔽。就让我们用实打实的数据分析与亲身经历,讲清楚公有云租赁模式的价值与陷阱 —— 在这个降本增效的时代中,供您借鉴与参考。



作者:非法加冯
来源:mp.weixin.qq.com/s/PgduTGIvWSUgHZhVfnb7Bg
收起阅读 »

WiFi万能钥匙突然更新,网友炸了

时至今日,机哥已记不清,七八年前曾用过哪些家喻户晓的手机软件。若不是最近看到这样一篇新闻。我都差点忘了,有一个名为“WiFi万能钥匙”的App曾风靡全国。当时机哥身边的亲朋好友,只要是有智能手机的。基本都会安装上这个App。原因倒是不复杂,在那个流量资费偏高的...
继续阅读 »

时至今日,机哥已记不清,七八年前曾用过哪些家喻户晓的手机软件。


若不是最近看到这样一篇新闻。


我都差点忘了,有一个名为“WiFi万能钥匙”的App曾风靡全国。


当时机哥身边的亲朋好友,只要是有智能手机的。


基本都会安装上这个App。

原因倒是不复杂,在那个流量资费偏高的年代。


咱们上网冲浪,主打一个“能蹭WiFi,绝不用流量


恰好,WiFi万能钥匙对用户最大的贡献,也是帮忙蹭网。


不管是人流量爆满的商城,还是学校办公室。


WiFi万能钥匙,总是能如它的名字般神奇,帮用户成功连上WiFi。


关键是,这软件还免费使用。


多少给当时懵懂的机哥,来了点小小的互联网震撼。



也是靠着“随时随地,免费上网”的优势。


WiFi万能钥匙发布不到三年,就拥有超过5亿的激活用户。


公司发的年终奖更是重量级。


给所有入职超过4个月的员工,送一台价值近百万元的特斯拉跑车。


什么叫风头无两啊,就是。


可随着时间推移。


越来越多用户也发现了,所谓的“免费蹭网”,是需要付出代价的。


在这些年的发展中,WiFi万能钥匙翻车过好几次。


包括被官方点名批评。


被华为小米轮番整治。


当时两大手机厂商,标记它为恶意应用,还把它赶出了自家应用商店。


再加上App内部,出现了各种离谱的广告。


不仅在形式上,集百家之所长。


摇一摇跳转、伪装跳过按钮、多图层套娃全凑齐了。


具体到广告内容,更是大杂烩乱炖。


不知道的,还以为下了个病毒软件呢...


尽管官方最近宣布,给WiFi万能钥匙减少70%广告。


但它这些年,积攒起来的崩坏口碑。


可不是一两个优化减负,就能抹掉的。


当然啦,如果只是广告讨人嫌。


那WiFi万能钥匙,还不至于被喷成这程度。


整个App的争议点,就在于它那“共享热点”模式。


没错,虽然它大名叫WiFi万能钥匙。


但它能帮咱们连上各种场合的WiFi,原理并不是暴力破解。


而是从自家密码数据库中,找到与该WiFi相匹配的密码。


等配对成功后,我们就成功蹭上别人的网络了。


官方也很清晰明了地介绍过,该App的运行原理:


软件基于共享经济,利用热点主人分享的闲置WiFi资源,向所有用户提供免费上网服务。

听起来,似乎是个不错的模式对吧。


这就好比,我在某个餐厅输入密码连上了WiFi。


然后WiFi万能钥匙,又把我手机记录下来的WiFi密码,上传到云端数据库,下次别人再来这家餐厅,直接打开App就能连上。


你帮我,我帮你,天下就没有难办的事儿了。


但理想很丰满,现实很骨感。


这共享模式,实际是很难落实下来的。


机哥举个例子啊。


在知乎上,有一个问题写着:


“如果每个人都给我一块钱,那我不就有13亿了吗?”


而且每人只需掏一块钱,也不是啥很大的损失对吧。


可这事儿就和共享WiFi密码一样,有一个大前提:


凭什么?


我凭什么无缘无故,给一个陌生人一块钱?


我又凭什么无缘无故,给一个陌生人,提供自家的WiFi密码?


更何况,是密码上传到一个装机量8亿的App。


对于WiFi万能钥匙来说,运营初期就面对着这个问题。


不过出来混,总得有两把刷子。


很快啊,就有网友对Wi-Fi万能钥匙做出了分析。


他表示,App可以直接从用户手机拿到WiFi密码。


搞机佬都知道,安卓系统在获取Root权限后,可以通过使用Re管理器等App,直接查看存放WiFi密码的文件。


可谓是明文存放,点开就送。


当然,能访问到这个文件夹的前提是,手机得有Root权限。


可很凑巧的是,早期的安卓手机获取权限非常简单。


随便在网上下载个“一键Root”工具,重启手机就完事儿。


所以在那个时候,用户第一次安装打开WiFi万能钥匙,都会被这App索取Root权限。


紧接着,最关键的问题来了。


它到底有没有,通过申请Root权限,来查看用户手机里的WiFi密码保存文件呢?


当时有位知乎老哥,特意反编译了1.0版本的WiFi万能钥匙。


发现了以下这几行代码。


作为一个,只会输入“Hello World”的代码废柴。


机哥还是很自觉地,把代码交给了AI去分析。


结果AI给出的分析,和那位知乎老哥的结论,几乎一模一样。


WiFi万能钥匙1.0版本,会在获取Root权限后,把手机上的WiFi配置文件,复制到了自己的缓存文件夹中。

嗯?难道说...


不过在后续的版本更新中。


WiFi万能钥匙的玩法严谨得多,主打一手正儿八经的“共享”。


比如把用户主动输入的密码存到云端库。


或者和运营商合作,把一些公共区域的免费WiFi给收录进去。


如果实在遇到一些,数据库里配对不上的WiFi。


WiFi万能钥匙还会提示你,可以尝试一下【深度连接】。


而所谓的【深度连接】呢,是App用内置的几千个弱密码,逐个连接同一个WiFi。


机友们都懂的,其实很多家庭路由器,密码都设置得很简单。


诸如12345678、1122334等朗朗上口的密码,简直不要太常见。


所以在很多时候,【深度连接】还真能帮你连上WiFi。


但后来的事情,咱们都知道了。


流量资费便宜了,用户对蹭WiFi的需求日渐下降。


再加上手机厂商和路由器厂商,也开始注重隐私安全。


Wi-Fi万能钥匙作为一个工具类应用,也就失去了解决问题的场景。


用户量减少、入下滑,都是板上钉钉的事儿。


为了维持收支平衡,WiFi万能钥匙加大了软件招商的力度。


我们可是有9亿用户总量的,欢迎来合作啊喂。


具体到可以塞广告的位置。


不能说克制,只能说处处皆是广告位。


横幅、图文、弹窗,基本上能塞内容的位置,都有广告的一席之地。


而WiFi万能钥匙,对于广告的内容筛选,更是让人汗流浃背。


比如说,以美女为诱惑,吸引你点开广告。


早期还有用户吐槽,App内部的信息流推送,有很多擦边低俗资讯。


讲道理,以它如此庞大的用户总量。


这么多广告的接入,肯定能让它在短时间内,赚得盆满钵满。


但这操作,多少有点饮鸩止渴的味道。


更何况,现在早就不是,流氓App能随意践踏手机的时代了。


你看这两年,手机厂商都在集中整治,WiFI类和清理类App存在的问题:


包括违规收集个人信息、频繁弹窗自动下载第三方软件等。


可能是意识到,只靠广告营收走不通。


WiFi万能钥匙在宣布改版后,广告确实少了很多。


那它现在又能靠啥维持生计呢?


机哥带着好奇,安装了新版打开体验。


结果发现,它现在往App塞了个短剧板块。


emmm...机哥也没啥好说的,祝它一切顺利吧。



作者:好机友
来源:mp.weixin.qq.com/s/9IfrA6ilpOit4dVAjH6U4Q
收起阅读 »

靠维护老项目度中年危机

最近靠维护老项目度过中年危机的话题挺火,刚好最近也在维护一个PHP开发的CRM的老项目,项目由于数据量比较大, 导致查询速度很慢, 经常出现超时的情况, 下面记录一下具体的优化过程。 优化老项目,老生常淡的几点: 1. 数据库优化 2. 代码结构优化 3. 缓...
继续阅读 »

最近靠维护老项目度过中年危机的话题挺火,刚好最近也在维护一个PHP开发的CRM的老项目,项目由于数据量比较大, 导致查询速度很慢, 经常出现超时的情况, 下面记录一下具体的优化过程。


优化老项目,老生常淡的几点:


1. 数据库优化
2. 代码结构优化
3. 缓存优化
4. 资源优化
...

数据库优化


众所周知, MySQL 优化第一步,就是建索引, 看了一下整个系统的表, 发现有大量的表都没有索引, 建了索引的表,索引名称有点花里胡哨, 如下:


contractId	`contacts_id`	NORMAL	BTREE	27599	A		0		
customer_id `customer_id` NORMAL BTREE 27599 A 0

--

index_group `role_id`, `callDate` NORMAL BTREE 4359069 A 0
business_id `business_id` NORMAL BTREE 518 A 0
status_id `status_id` NORMAL BTREE 43 A 0


于是,优化第一步,规范一下索引的命名,MySQL索引的命名虽然没有硬性的规范,但是修改一下自己看着舒服, 个人理解:


普通索引:idx_字段1_字段2
唯一索引:uk_字段1_字段2
主键索引:pk_字段1_字段2


于是 上面的索引改成了:


idx_contacts_id	`contacts_id`	NORMAL	BTREE	27599	A		0		
idx_customer_id `customer_id` NORMAL BTREE 27599 A 0

--

idx_role_id_callDate `role_id`, `callDate` NORMAL BTREE 4359069 A 0
idx_business_id `business_id` NORMAL BTREE 518 A 0
idx_status_id `status_id` NORMAL BTREE 43 A 0


一下看起来舒服多了, 于是, 优化第二步, 就是给没有索引的表加上索引, 这个工作量比较大, 先把几个 常用功能模块的 表给加上索引, 于是 吭哧吭哧的 分析了 2天的 慢日志, 给需要加索引的表加上索引,本以为 加完索引后, 查询速度会快很多,结果发现, 并没有什么卵用. 一个页面 虽然快了点, 但是 不是太明显.


本着能加 配置 绝不改代码的原则,先去问了一下运维 Mysql 运行的机器内存是多大 64G. 这么大,那好办,先分析一下 数据库中的表引擎. 上了一段代码:


/** * Author: PFinal南丞 * Date: 2023/12/28 * Email:  *//** 确保这个函数只能运行在 shell 中 **/if (!str_starts_with(php_sapi_name(), "cli")) {    die("此脚本只能在cli模式下运行.\n");}/** 关闭最大执行时间限制 */set_time_limit(0);error_reporting(E_ALL);ini_set('display_errors', 1);const MAX_SLEEP_TIME = 10;$hostname   = '';$username   = '';$password   = '';$connection = mysqli_connect($hostname, $username, $password);if (!$connection) {    die('Could not connect: ' . mysqli_error($connection));}$query  = "SELECT table_name,engine FROM informati0n—schema.tables WHERE table_schema = 'smm';";$result = mysqli_query($connection, $query);if (!$result) {    die("Query failed: " . mysqli_error($connection));}$InnoDB_num = 0;$MyISAM_num = 0;while ($process = mysqli_fetch_assoc($result)) {    echo $process['table_name'] . " " . $process['engine'] . PHP_EOL;    if ($process['engine'] == 'InnoDB') {        $InnoDB_num++;    }    if ($process['engine'] == 'MyISAM') {        $MyISAM_num++;    }}echo "InnoDB " . $InnoDB_num . " MyISAM " . $MyISAM_num . PHP_EOL;mysqli_close($connection);

得出结果:


表引擎 MyISAM 的表 176 张 InnoDB的表引擎 88张. 要了一份 线上MySql 的配置发现:


...

key_buffer_size = 512M
innodb_buffer_pool_size = 2048M

...


都知道 innodb_buffer_pool_size 针对的 是 InnoDB的表引擎,key_buffer_size 针对的 是 MyISAM的表引擎. 这配置不得修改一下. 果断打申请, 申请修改线上配置.


...

key_buffer_size = 2048M
innodb_buffer_pool_size = 2048M

...


重启服务后,果然比原来快了好多.能撑到 同事不在群里 打报告了.


艰巨的长征路迈出了第一步,接下来,本着 死道友不死贫道的原则, 厚着脸皮,让运维帮忙整了一台mysql 的机器,来做了个主从分离。 速度一下,不影响业务的正常使用了.


接着 开启漫长的 优化之路.


缓存优化



  1. 项目没有开启数据缓存, 只有 代码编译的缓存


所以这一块是一个大的工程, 所以先不动, 只是 给 几个 常用的功能加了一个 数据 的 缓存。后续的思路是:


  a. 加一个 redis, 使用 把代码中的统计数据 缓存到 redis 中

b. 把客户信息,客户的关联信息,组合到一起, 然后缓存到 redis中.
....


代码结构优化


开始挖开代码, 看看 查询慢的 功能 代码是咋写的,不看不知道,一看直接上头:



  1. 几乎全是 foreach 中 的 SQL 查询:


    foreach($customer_list as $key=>$value){        # ......        $customer_list[$key]['customer_name'] = $this->customer_model->get_customer_name($value['customer_id']);        $customer_list[$key]['customer_phone'] = $this->customer_model->get_customer_phone($value['customer_id']);        $customer_list[$key]['customer_address'] = $this->customer_model->get_customer_address($value['customer_id']);                # ......    }


  2. 由于 ORM 的方便复用, 大量的 表关联模型 复用,导致查询的 废字段特别多.比如:


    <?php    class CustomerViewModel extends ViewModel {        protected $viewFields;  public function _initialize(){   $main_must_field = array('customer_id','owner_role_id','is_locked','creator_role_id','contacts_id','delete_role_id','create_time','delete_time','update_time','last_relation_time','get_time','is_deleted','business_license');   $main_list = array_unique(array_merge(M('Fields')->where(array('model'=>'customer','is_main'=>1,'warehouse_id'=>0))->getField('field', true),$main_must_field));   $data_list = M('Fields')->where(array('model'=>'customer','is_main'=>0,'warehouse_id'=>0))->getField('field', true);   $data_list['_on'] = 'customer.customer_id = customer_data.customer_id';   $data_list['_type'] = "LEFT";   //置顶逻辑   $data_top = array('set_top','top_time');   $data_top['_on'] = "customer.customer_id = top.module_id and top.module = 'customer' and top.create_role_id = ".session('role_id');   $data_top['_type'] = "LEFT";   //首要联系人(姓名、电话)   $data_contacts = array('name'=>'contacts_name', 'telephone'=>'contacts_telephone');   $data_contacts['_on'] = "customer.contacts_id = contacts.contacts_id";   // 检查是否存在部门库字段            $warehouse_id = I('warehouse_id', '', 'intval');            if ($warehouse_id) {                $warehouse_id = D('Fields')->isExistsWarehouseTable(1, $warehouse_id);                if ($warehouse_id) {                    $customer_warehouse_data_table = customer_warehouse_table($warehouse_id);                    $warehouse_data_list = M('Fields')->where(array('model'=>'customer','is_main'=>0,'warehouse_id'=>$warehouse_id))->getField('field', true);                    $warehouse_data_list['_on'] = 'customer.customer_id = ' . $customer_warehouse_data_table .'.customer_id';                    $warehouse_data_list['_type'] = "LEFT";                    $this->viewFields = array('customer'=>$main_list,'customer_data'=>$data_list,$customer_warehouse_data_table=>$warehouse_data_list,'top'=>$data_top,'contacts'=>$data_contacts);                } else {                    $this->viewFields = array('customer'=>$main_list,'customer_data'=>$data_list,'top'=>$data_top,'contacts'=>$data_contacts);                }            } else {                $this->viewFields = array('customer'=>$main_list,'customer_data'=>$data_list,'top'=>$data_top,'contacts'=>$data_contacts);            }  }    ?>


  3. 代码中的业务逻辑一直再叠加,导致废代码量特别的大需要重新梳理逻辑


针对以上的代码做修改:


a. 第一点, 把所有foreach 中的 sql拆出来,先去查询到内存中,然后组合减少sql语句 

b. 第二点, 简化 ORM的乱用,比如只需要查询一个字段的 就直接用原生sql或者新的一个不关联的orm 来处理

资源优化



  1. 由于录音文件过大, 找运维 做了一个专门的文件服务器,移到了文件服务器上


最后


最后,给加了个定时任务告警的功能, 方便及时发现异常, 优化的 第一步 勉强交活。剩下的 优化 需要再花点时间了,慢慢来了.


作者:PFinal社区_南丞
来源:juejin.cn/post/7353475049418260517
收起阅读 »

高龄程序员转换开发语言的心酸历程

高龄程序员转换开发语言的心酸历程 35岁,对于大多数程序员来说,正处于职业生涯的黄金时期。然而,对于我来说,却是一个充满挑战的转折点。在做了10年的PHP开发工程师之后,我决定转战Java开发。 初衷: 做出这个决定并非易事。一方面,我对PHP已经积累了...
继续阅读 »

高龄程序员转换开发语言的心酸历程


35岁,对于大多数程序员来说,正处于职业生涯的黄金时期。然而,对于我来说,却是一个充满挑战的转折点。在做了10年的PHP开发工程师之后,我决定转战Java开发。


初衷:


做出这个决定并非易事。一方面,我对PHP已经积累了丰富的经验,拥有稳定的工作和收入。另一方面,随着互联网技术的不断发展,Java以其强大的性能和广泛的应用前景,逐渐成为主流开发语言。为了不落后于时代,我意识到学习Java是势在必行的。


挑战:


然而,转行并非一帆风顺。与初出茅庐的年轻人相比,我面临着更大的挑战:




  • 学习压力:Java与PHP有着很大的不同,需要从头开始学习新的语法、框架和生态系统。


  • 时间成本:除了日常工作,我还要抽出时间学习Java,这对我来说是一项巨大的考验。


  • 心理压力:年龄和经验带来的压力,让我一度怀疑自己是否能够成功转行。


心酸:


在学习的过程中,我经历了许多心酸的时刻:





  • 为了理解一个概念,我连续熬夜几天,最终还是一头雾水。



  • 在面试中,被年轻的求职者比下去,让我感到深深的自卑。


坚持:


尽管困难重重,但我从未想过放弃。我深知,只有坚持才能实现自己的目标。





  • 我制定了详细的学习计划,并严格执行。



  • 我积极参加技术交流活动,向优秀的程序员学习。



  • 我不断给自己打气,鼓励自己坚持下去。


转机:


上天不负有心人,经过一年的努力,我终于掌握了Java开发的基本技能。





  • 我顺利通过了Java工程师的面试,获得了新的工作机会。



  • 我在新的岗位上快速成长,得到了同事和领导的认可。



  • 我用自己的经历证明了,年龄不是转行的障碍,只要坚持不懈,就一定能够成功。


感悟:


这次转行经历让我深刻地体会到:





  • 学习是程序员的终身事业,只有不断学习才能保持竞争力。



  • 年龄不是问题,只要有决心和毅力,就能够克服任何困难。



  • 坚持不懈是成功的关键,只有坚持才能实现自己的目标。


希望我的经历能够鼓励更多高龄程序员勇敢追梦,在职场上取得更大的成就!


忠告:


如果你也想转行,以下几点建议或许对你有所帮助:





  • 做好充分的准备,了解目标语言的技术体系和发展前景。



  • 制定详细的学习计划,并严格执行。



  • 积极参加技术交流活动,向优秀的程序员学习。



  • 不要害怕失败,坚持不懈才能实现目标。


最后,我想说的是,年龄只是一个数字,只要你有一颗热爱编程的心,就永远不会被时代淘汰!


作者:源梦倩影
来源:mdnice.com/writing/48740efaaeaf48128397471867705c9a
收起阅读 »

一碗水永远不可能端平

和一些朋友聊天的时候,他们总是会说领导对自己是怎么不公平了,脏活累活丢给自己干,好处还一个也没拿到,而对别人是如何如何好了,表现得自己很无辜,很委屈的样子。 我觉得如果感觉不舒服,要么寻求其他方式来平衡,要么趁早离开,因为想寻求所谓的公平,那简直是说笑话。 很...
继续阅读 »

图片


和一些朋友聊天的时候,他们总是会说领导对自己是怎么不公平了,脏活累活丢给自己干,好处还一个也没拿到,而对别人是如何如何好了,表现得自己很无辜,很委屈的样子。


我觉得如果感觉不舒服,要么寻求其他方式来平衡,要么趁早离开,因为想寻求所谓的公平,那简直是说笑话。


很现实的问题,一个女人生下两个孩子,虽然表面都会公平对待,但是内心肯定都会更加喜欢长得好的那个,这就是人性的私心。


读书的时候,你成绩好不一定能赢得老师的喜欢和照顾,但是如果你家境很好,并且父母经常给老师拿烟拿酒,经常约老师出去吃饭喝酒,那么大多数老师肯定都会对你照顾。


这就是人性,哪里有那么多公平对待,无非是价值提供得多不多而已。


这个社会无论情感还是物质,都是十分倾斜的,钱都是流向越有钱的,爱都是流向越不缺爱的。


你说以前的政策是农村包围城市,先富带动后富,大家都觉得行,但是现在看一下,真的带动了吗?


从教育资源就能看出来,北京的一所公立学校和贵州乌蒙山区的一所公立学校的基础设施,经费,师资力量,那简直是一个在天上,一个在地下。


社会层面尚且都不能做到一碗水端平,更何况个人呢?


记得刚工作的那一年,我和一个女同事同一天入职,另外一个架构师比我们早十来天,但是到了第二年,发年终奖的时候唯独没有我们两个,并不是我们工作不辛苦,不努力,但是不给你就是不给你。


当时我还找领导理论,说为啥不一碗水端平,为啥要区别对待?


但是有用吗?合同上也没有明确规定要给你发年终奖,所以你再怎么说也没用,只有不欢而散。


另外一个早入职的同事虽然拿了年终奖,但是是别的同事四分之一,并不是他工作不努力,做的活没别人多,奉献的力量没别人大。


但是在人性和资本面前,并不是你像一头老牛一样辛苦你就能得到和别人一样的对待。


可能有一些没做啥事,但是会来事,在关键节点上会露面的人,人家却得到了不错的对待。


这时候你作为一个底层的小员工,可有可无的人,你去谈公平对待是会显得很无力的。


所以要尽早走出一碗水端平这个误区。


无论是工作,家庭还是社交,把价值进行可视化才能占风头,低头苦干只有感动自己。


因为我们如果把角色进行转换,自己可能还不如别人做得好,只是自己段位比较低,容易去做一些无力的咆哮而已。


因为人这种生物在自己没有受益的时候,都是会说别人不好,别人不公平公正,但是自己受益了,别人怎么做都觉得对。


就像我们经常说有些人在某些岗位上拿着钱不作为,简直是吃皇粮不干事,无情的骂别人。


但是当你到了那个位置,你就能保证你有作为,你认真负责,也不见得吧!


所以想清楚这一点就不会活得那么累,就会泰然自若面对身边发生的事情,就会摒弃那些自以为是和幼稚的想法!


作者:苏格拉的底牌
来源:juejin.cn/post/7337188759059824655
收起阅读 »

调了个方法导致接口变慢好多,真实原因有点坑。

前言 这篇文章是按照我的记忆梳理的,然后解决方法其实很简单,主要是梳理一下当时的排查思路,所以请大家多多指教。错误之处或表述不清楚的地方,欢迎评论指出或建议,感谢。 背景 事情发生在一个正常的下午,领导对我说:有项目组汇报说一个创建的接口变的比较慢,让我...
继续阅读 »

前言



这篇文章是按照我的记忆梳理的,然后解决方法其实很简单,主要是梳理一下当时的排查思路,所以请大家多多指教。错误之处或表述不清楚的地方,欢迎评论指出或建议,感谢。



背景



事情发生在一个正常的下午,领导对我说:有项目组汇报说一个创建的接口变的比较慢,让我尽快排查一下。我一听,这个功能不是我写的,心里首先放松一下,那就排查吧!



验证线上


首先,当然是和领导确认,什么情况下,访问这个接口慢,因为有时候可能在某个特殊的场景下才会导致此类问题,或者是偶发情况,确定了这一点,也方便排查,然后我就按照领导说的,找到所属的数据页面,进行同样的操作。发现果然比较慢(这是我工作中学到的,不管别人怎么说,自己验证一遍),F12看了下,返回时间差不多快2s了,这个速度确实是有点慢的,因为这个添加的处理逻辑按理来说是不复杂的,不应该这么慢。


本地排查


接下来,就是排查的步骤,首先本地先启动一下,连接测试库看看是否有慢的问题,如果本地也慢,就比较方便一些,可以通过日志来打印每一部分花费的时间(我一般用StopWatch类),就可以知道哪里慢了。但是遗憾的是本地没有复现这种情况。


代码排查


既然无法复现,就只能看代码了,对比了下涉及到这个文件的提交记录,大概伪代码如下:


...
...
String name = xxxService.getMember(name);
...
Project project = prjService.getProject(code);
...
project.getProjectId();
...
...

看见的第一眼,我直接忽略了这一段,觉得没啥问题啊,然后事实证明,事出反常必有妖。


最终原因


其实慢的原因就是我直觉忽略了的这一段代码中的Project project = prjService.getProject(code);,当我点进去后我才发现,里面别有洞天,我没法给大家复制代码,还是给大家一个伪代码:


....
Project project = prjDao.getObject(code);
String pId = project.getProjectId();
List<Task> list = prjDao.queryTaskList(pId);
for (Task task : list){
String taskId = task.getTaskId();
Work w = prjDao.getObject(taskId);
....
s = s.apend(w.getName());
}
project.setExtend(s);
....


以上代码存在的问题主要就是在for循环中进行对数据库的查询,如果list的长度很长的话,就会导致查询慢的问题,当时发现的时候真的是无语了,你如果有扩展,可以在方法中进行清晰的标识(比如:queryprojectExtend),并且代码也不必这么写,可以提取所有的taskId到一个list中,然后作为参数进行查询。


另外还有一个坑的点就是,其实原来的人调用这段方法本身其实就是为了拿一个project.getProjectId();,所以完全可以另外写一个简单获取的方法即可。


解决并验证


因为知道了原因,所以从数据库找了数据比较多的一个来进行复现,果然复现成功,也证明了问题就是出在这里。
首先把代码进行修复,修复后的伪代码如下:


....
Project project = prjDao.getObject(code);
String pId = project.getProjectId();
List<Task> list = prjDao.queryTaskList(pId);
List<String> idList = list.getIdLIst(list);
List<Work> works = prjDao.queryObjectsByIds(idList);
for (Work task : list){
s = s.apend(w.getName());
}
project.setExtend(s);
....

以上虽然也使用了for循环,但是内部只是做了字符串的拼接,也可使用Stream,会更简洁。
更改完后,继续测试该接口,发现是正常的。


思考总结



其实这次的问题很简单,没有涉及到高大上的一些问题来调整,要避免其实也很简单,调用其他人写的方法时,大概点进去观察一下。写方法的时候多想一下,是否会造成查询慢的问题,就可以了。




  • for循环查询这种情况,尽量避免。

  • 调用他人方法时需要知道内部大概的逻辑,切勿望文生义。

  • 不要想当然,觉得没问题就不排查。


致谢


感谢你的耐心阅读,如果我的分享对你有所启发或帮助,就给个赞呗,很开心能帮到别人。


作者:bramble
来源:juejin.cn/post/7348842402826321961
收起阅读 »

为什么马斯克能扭曲现实

好多人看完Elon的新传记开始扯现实扭曲立场,聊虚头巴脑的东西都没用,关键是为什么Elon有这种来扭曲现实的能力。   马斯克手下的工程师的bar都非常高,早期在SpaceX为了不雇二流工程师宁愿自己上,想要push下面这些人拼命工作,要没点真本事基本不可能,...
继续阅读 »

好多人看完Elon的新传记开始扯现实扭曲立场,聊虚头巴脑的东西都没用,关键是为什么Elon有这种来扭曲现实的能力。


 


马斯克手下的工程师的bar都非常高,早期在SpaceX为了不雇二流工程师宁愿自己上,想要push下面这些人拼命工作,要没点真本事基本不可能,分享几个例子(在实际的工程和制造过程中大概率是常态):


 


Gega Factory流水线上,本来用6颗螺丝固定的地方,Elon觉得4颗就够了,下面的工程师解释说再少的话强度不够,Elon说他在脑子里模拟了一下冲压强度,感觉4颗螺丝就顶得住,改完后一切正常运行,这种判断需要大量的工程经验和物理直觉。


 


SpaceX开始制造星舰的时候,火箭材料的选择上争议很多,团队告诉他用不锈钢会比用猎鹰9号上的锂铝合金或者碳纤维更重,Elon的直觉告诉他不是这样,要求团队把具体数字算出来,结果Elon是对的,而且不锈钢在极寒条件下强度会增加50%,更适合装载超低温液氧和液氮,再者他可以雇佣没有碳纤维经验的工人(用工的成本更低),更进一步不锈钢的熔点高,星舰的外壁不用额外设置隔热层,最后焊接还更容易(锂铝合金需要超净焊接环境,不锈钢直接露天大棚咔咔焊)。更细节的是,要确认星舰外壁的厚度时,一线的焊接工人给Elon的反馈是4.8mm,Elon觉得4mm就行,不顾一线人员的担忧拍板了,后来证明没问题。


 


Elon在SpaceX内部普及了一个概念叫"白痴指数",指的是一个零件或组件的总成本和原材料成本之间的比值。他在会上问下面的工程师根据⽩痴指数,猛禽发动机中做得最好的部分是什么,结果下面的人答不上来,试探性地答了一个喷管护套,说成本大概13000美元,由一种钢整块制成,Elon追问这种原材料的价格是多少,对方回答说大约几千美元,Elon立马纠正说200美元现场打脸并表示对方错的离谱。


 


现实扭曲立场是什么?就是你老板在你的工作领域很多地方比你还懂,角度比你还新奇,考虑比你还全面,对细节数据掌握比你还扎实,在过往的技术方向,工程方案,成本控制的争论中超出大家的预期,证明他更正确。假想一下这种老板要求员工把某个指标在某一期限内优化xx%,或者彻底拿出一个更好的方案,员工说不可能,然后老板自己住在工厂加班最后有理有据prove you wrong是什么感觉?下一次他再提一个看起来是扯淡的需求,团队就会觉得这是可能的,然后work hard on it,这就是现实扭曲立场。


 


如果leader本人没有这种身先士卒的精神,以及让最好的工程师都赞叹的专业能力,能扭曲个啥?喊几句cheap slogan谁都会


 


不是说Elon是神,他也会犯错误,比如2018年Model3产能爬坡的时候在工厂自动化上面做的过于激进,反而降低了效率(比如某些机械臂在搬运物件的时候出现意外导致整个产线停滞,用手工可靠得多),最后为了最大化生产效率又开始"去自动化"。类似地,在收购SolarCity早期,他疯狂push下面的人增加屋顶太阳能面板的安装效率,搞了半天也没什么成效后来不了了之。但这些错误都是可以接受的,都不妨碍他在团队塑造硬核文化然后drive整个公司往前走。


 


那些故事性很强的鸡汤鸡血都是扯淡,事实很简单,就是Elon在技术和商业上认知几乎比所有人都好。


作者:数据智能老司机
来源:juejin.cn/post/7351430820715266074
收起阅读 »

生命里每一段记忆,可能都伴随着DNA的断裂与修复

周末的时候刷到一篇论文,可能揭示了人类长期记忆的形成机制。而这机制的背后似乎是生命的本质。 Nature上的新研究 这是一篇新鲜热乎的Paper,3月27号刚发的。(P.S.:Paper原地址我放原文链接里了) 图源:Nature ...
继续阅读 »

周末的时候刷到一篇论文,可能揭示了人类长期记忆的形成机制。而这机制的背后似乎是生命的本质


Nature上的新研究


这是一篇新鲜热乎的Paper,3月27号刚发的。(P.S.:Paper原地址我放原文链接里了)



图源:Nature

图源:Nature


这个题目是说记忆构成和TLR9通路中的DNA感知的关系





不是说最近大模型Kimi很火,支持200万字无损上下文了么,于是我直接上Kimi试一下。



图源:Kimi

图源:Kimi


嗯,上传上去稍微问一下整体架构和结论,还是挺有意思的。说的似乎是记忆和DNA的关系。但来来回回问Kimi感觉还是挺花时间,算了还是自己看看吧。


我尽量试着给大家解释解释。


长期记忆和DNA损伤


这篇Paper里的核心是一个反直觉的结论是:在人类大脑海马体形成记忆的过程中,一些细胞会产生损伤,尤其是双瓣DNA会产生断裂和重组


也就是说,记忆的产生本身对人体来说,并不是获得,而是损伤。


是不是非常反直觉?


这个Paper里的研究思路很明确。结论也非常直接。


就是在记忆形成的短期内(大概1-2个小时内),大脑中负责记忆的部分会经历一个“破坏的过程”。这个过程堪称惨烈。比如双链DNA会产生断裂、细胞的瓣膜会产生破裂,甚至还有一些细胞核里的组蛋白会流到细胞核外,同时伴随着一些“炎症反应”。



图源:Nature

图源:Nature


很多人看到“炎症反应”会觉得是发炎,但其实不完全是。学术上的炎症反应指的是“损伤、抗损伤和修复的动态过程”。


那么,在记忆产生这个撕裂的过程中的炎症反应里扮演重要角色的就是这个论文的主角:TLR9


它是一个特定的免疫机制,正是它在这个过程里去修复DNA断裂,修补破裂的细胞并且应对炎症反应。



图源:工作细胞

图源:工作细胞


这也就是说,每一次记忆的形成,都是一个DNA断裂、细胞破损、然后TLR9处理炎症反应、最后身体恢复正常的一个过程。


研究人员还尝试了移除TLR9。于是发现在没有TLR9的情况下是无法形成长期记忆的,也就是说这个作用链条没有TLR9的参与就没法闭环。


听起来这有点像健身锻炼肌肉,肌肉的增长前提是轻微肌肉撕裂


但不同的是,对于锻炼肌肉而言,只有在训练和运动的时候才会出现这样的情况,并且是轻微肌肉撕裂。对于记忆过程中这都不是轻微撕裂了,这是双链DNA断链再重组。


锻炼=断链了属于是。


Viva La vida


我并不是一个专业的医学生,也不是生物专业的研究人员。我只是看到这篇Paper,突然对人类的生命再一次肃然起敬。


我们都觉得体育运动和锻炼带来的酸爽是一种正向反馈,因为这是你的身体在经受一次又一次的挑战与自我修复。


但是在我们看不见的地方,在你记住一些知识、一些任务和一些事情的时候,每一分每一秒身体里都有数以万计的细胞再断裂、产生炎症、再重组。


涅槃在时时刻刻都确实发生着。原来不思考的生命就没有意义,这不是一句鸡汤。


生命的自然机制本身就在挑战、摧毁并重塑自己。我的身体比我自己对自己可狠多了。


Viva la vida是一句西班牙语,意思是生命万岁/致敬生命。



图源:Google

图源:Google


这幅画的名字就叫做《Viva La Vida》,受这幅画和一些历史故事的启发,ColdPlay乐队创作了他们的经典专辑《Viva La Vida》.


所以现在我知道了,那些所谓刻在脑子里的事情,是真的literally的“”在了我的生命里。


作者:wayne3200
来源:mdnice.com/writing/84234c4f5f1c479a920b9103bf1f09f3
收起阅读 »

研究生真的会勾心斗角嘛?

背景 我感觉我是一个有点大大咧咧的人,有时候看不出来别人对我耍心眼,大学期间也有几次是事后才反应过来,而且我很容易对别人真心相待,我觉得我对他好他也会对我好,起码不会坏我,但是并不是这样,最近被好多研究生勾心斗角的言论吓到了,真的很怕 编者语 但什么东西...
继续阅读 »

背景


我感觉我是一个有点大大咧咧的人,有时候看不出来别人对我耍心眼,大学期间也有几次是事后才反应过来,而且我很容易对别人真心相待,我觉得我对他好他也会对我好,起码不会坏我,但是并不是这样,最近被好多研究生勾心斗角的言论吓到了,真的很怕


编者语


但什么东西有利益分配的时候,那么心眼就已经在耍起来了。


大家虽然,但也不会有啥坏心眼,不至于为了自己利益给其他人使绊子。


所以,放宽心,一切都是纸老虎。勇敢面对。


对了。多数人都很单纯,大家都是好朋友,以心换心,你是什么样的,你身边的人也会是什么样的。





把“嘛”字去掉





答案是肯定的,研究生真的会勾心斗角!


有人的地方就会有江湖,你的寝室就四个人还会有好几个小群,更何况一个有好多人的课题组呢?


举个例子:某校大牛课题组学生加职工共计100人,其中小导5个,博士10个,科研助理类工作人员3个,剩下的都是硕士和本科实习生。


大导分配任务给小导的时候会把同一个课题给到两个人,这不就出现矛盾了么?这两个人都需要成果,肯定谁做的快谁能留下,那他们带的研究生不就被迫跟着站队了么?难道你敢私下跟另一个导师的同学说你们组课题进展?或者说实验计划?


加上课题组内部的博士名额有限,想要读博的硕士本身就有很大的竞争关系,这不要靠谁的科研成果多,或者说谁能更得导师的心来决定了?


然后就是奖学金啊、课题组里面的资源啦、实验排期啦、仪器使用啦………能产生利益冲突的不要太多了好不好。


没有永远的朋友,只有永远的利益不仅仅适用于国家之间的关系,在职场或者读书阶段也是如此。


9个女生,1个男生


我们组研123年级一共9个女生,1个男生。1女博5。勾心斗角情况数不胜数。尤其是读到博士阶段且在校时间很长的尸姐(兄),及其擅长利用师弟师妹帮其做实验push 你控制欲极强,然后和老板聊天笑着就把你告了。说你经常找不到人做实验粗去玩。。。


大虎不怕,苍蝇难防


大部分人都是好的。但难免遇到一两个苍蝇。一个人能做到让组内的其他人都对他有意见有看法,是真的不容易。


大勇若怯,大智如愚。


会有的,而且同门有可能会成为打到你的主谋。我读研的时候,当年考研初试复试第一的女生就因为锋芒尽显,在上课做pre和各种提问中锋芒毕露,在组会上也比较积极,给人一种远超同门的气场。结果就被同门联合她的舍友诱导说了一些质疑导师的话,被录音给了她的导师,直接被逼退学,后面运作了好久才转组成功(也没有科研前途了,去给别人当耗材牛马去了,成果不给她的那种)。


大勇若怯,大智如愚。我反正就不会在没啥用的课堂演讲上锋芒毕露或者提问把同学问的下不来台。自己学点喜欢的东西,不争不抢,期末考试考好点,科研做好点,能在没人指导和导师起副作用情况下能写出大小论文通过答辩就行了。


研究生是否勾心斗角甚至是导学关系是否勾心斗角很大程度上取决于学院的整体生态和科研环境。如果你的学院和课题组大部分人都容易沟通、实事求是、科研风气积极向上,那必然不需要花很多时间处理所谓的人际关系。但如果你所在的学院和课题组学风不正,大部分事情讲的是丛林法则,凡事一看关系二看派系三看资源的。那大概率是要花很多时间在人际关系、派系斗争和做局坑人上。毕竟你勤勤恳恳做1000个小时得到的结果,可能别人花2小时编一个谣言或者给导师拍拍马屁就可以直接抢走,换谁会愿意真正的干活呢?


恶心


自己的idea被实验室同学拿去发了论文,顶会,作者没有我,甚至都没有收到一句感谢,并且所有场合提到这个idea的时候都变成了他的,老师不知道会当着我的面说那个同学idea怎么怎么好可以用在什么什么上拓展一下,我该如何自处?!实验室的同学还劝我大度,我大度你个鬼啊!不知道算不算恶心?


还有人明明知道某个代码怎么回事,还故意告诉你错的,实验室有锅往你身上甩,有功劳自己抢的可快了,肆无忌惮的的欺骗,偷抢功劳,算不算恶心?


本人一直秉着实验室都是好同学的思想,大家有求一定100%努力相助,从不欺骗谁,不抢别人功劳,觉得实验室应该互相帮助,一起科研进步,最后却还是遇到上述那些人,呵呵呵。


最难的地方是老板


有感而发。


说几句吧。


国外实验室呆过,感觉就是没有什么勾心斗角。


一个团队的人都很乐于互相帮助。


发文章一块发,有工作贡献就可以。当然主要作者都是博士生。


实验室的人际关系,很简单,很和谐。从无欺负人现象。


听说,国内什么都很卷。


就想说说,到底什么是卷。


有的人说,是蛋糕不够分。


有的人说,是美国卡脖子。


什么的。各种说法都有。


看过各位的回答,有点明白到底什么是内卷了。


就是一个实验室的人,没有爱心,也缺乏互帮互助的精神。


当然,很多精力就要花费在维护人际关系,维护实验室基本操作规范方面了。


这个比较普通与简单的方面,其实都没人重视,也不认真去履行。


实际上,是实验室人员缺乏职业道德,缺乏职业精神。


另外,感觉国内实验室人员缺乏主人翁意识,别人的事情不管,其实别人的事情很大程度也是与自己有关的。因为一个实验室嘛,互帮互助,这是人性。


还有,精力浪费在人际关系方面,就是没有很多精力用于科技研发,科研想法的创新了。


这是个人理解的所谓内卷。


我觉得不是硬件的问题,是软件的问题,就是人之根本的问题。


科学的发展,其实是人的发展。


科学之所以在西方,欧美发展的繁荣,也是因为这些地方,首先是人得到了发展。


人性得到了发展,人的本能得到了发挥与发扬。


人有哪些本能呢?


作为国外观察,我觉得人的本能有很多就是根本性的,却在国内一些实验室可能严重缺乏了。


比如,敬业,负责,有爱心,互帮互助,团队精神,自我批判与质疑,对待他人宽容与谅解,等等。


这些人的本能是维护一个实验室正常高效运转的基本要素,实验仪器其实反而是次要。


实验室里最宝贵的财富,是人。仪器什么的,都可以造,买,借。


只有人,如果本能受到了破坏,则就很难修复。想让一个不负责任各种撒谎的人突然就负责然后特别的敬业严谨,可能需要好几年的培养。而一个出了问题的仪器,花钱修理或者直接购买就行了。


可见,人的本能,难以重建与塑造。


那么发生在一个实验室里的各种内卷情况,则会层出不穷。


一个人的环境良好的实验室,哪怕实验仪器老旧,只需要多付出一点精心维护,实验室还是可以正常运作的。甚至可以发挥出更大的价值。


一个人的环境不好的实验室,哪怕是几百万几千万的大价钱购买的顶尖仪器,恐怕也难以得到足够的维护与修养,从而得不到一个实验仪器应有的功效。


那么如何解决实验室勾心斗角难题呢?


我觉得挺难的,不过还是可以尝试一些办法去解决。


第一,多去国外实验室打工,交流,学习。谦虚点,多观察,尤其多观察国外实验室他们如何管理的。人与人如何搞关系的。肯定和国内不一样。另外,不要觉得在国外,类似国内不好的事情也一样发生,就对国外实验室或科研产生看不起瞧不上的心态,这样只能自己心浮气躁,什么都学不到。最多混个履历或者文章。


第二,提高一下心性。其实冥想之类的挺管用。别人的批评听听,多吸取积极的批评,负面的批评就早点忘记,不要影响自身的积极性。


第三,多阅读一些有关,心灵,精神,方面的书籍。最好还是看国外翻译的。国内很多都是比较假的鸡汤。


第四,组织实验室共同学习,共同进步,多互相帮助,做事有规则有原则,就可以减少很多根本不必要的勾心斗角与内卷。


第五,以身作则,遇到原则问题需要自己去维护自己的利益,同时,要影响实验室其他成员给积极的影响。


当然,最难的部分实际上是实验室老板。这个,我们就无法解决了。如果老板愿意听你的,可以自己去与老板谈谈如何更好构建实验室。也是一个办法。


如果老板固执的不行,只能换地方了。


往大了说,这个内卷问题其实是一个文化问题。


这就太难解决了。谁也解决不了。


到了自己头上


本来以为自己不会有这样的问题的,一年以后发现实验室可真是卧虎藏龙小型帮派现场啊。


实验室大概有两个势力集团,一靠权力,二靠暴力,剩下我们普通人苦苦挣扎,现在新生还好真怕和他们的师兄师姐变得一样。作为有很多老师的大课题组,财产掌握在刚刚留校的实验室大师兄手中,暴力是指实验室有两位博士(男女朋友)逐渐将财产私有化专门化并欺压师弟师妹们。还有其它普通人分在别的老师名下我觉得我们同病相怜惨兮兮。还有师妹实验数据的文件夹被整个删了不知道是谁。


先说大师兄手下的特权,因为大师兄享有采购权所以在导师极度抠门的情况下,资源优先分配到人家那里。一个实验室手套都不能随时供应你敢信?三角瓶也不够要到处借,洗衣粉没了也不及时买(我去一楼借洗衣粉人家说只有洗衣液留下了羡慕的泪水。)试剂随时就没了,还有各种耗材没有是正常操作,(称量纸没了撕笔记本,洗手液没了就不用,甘油管没了找别的实验室借,枪头没了洗洗灭菌,橡皮筋没了把断了的打个结继续用,冰箱保菌装甘油管盒子没了拿硬纸盒装)


但是到了大师兄手下就不一样了,反正我一问就是没有了买了还没回来,但是人家就有一箱一箱的新三角瓶,随时可用的手套,有充足理由实验需要采购各种东西。还有年度大会两三千的奖励为实验室做贡献而其它师兄师姐比如负责每晚安全检查和新生培训的就没有。


那两口子不属于大师兄管但是是博士入学久,所以就自己给自己特权。两口子有自己专属的超净工作台,工作台要预订,我们也可以用但是只要人家要用没定也会在旁边赶你。PCr要预订,一个学弟延伸时间久,师姐就直接把他的PCr管扔了出去扔了出去还给负责学弟的师兄(有事不在学校)打电话骂了半个小时问反应体系延伸时间是放迟了还是超时了,此时还有半小时反应完成。他们组所有公用的东西自己都会私藏一份作为人家专用的东西,小到量筒,浮漂,放三角瓶的框,大到蛋白胶的电泳槽,写了他们名字的别人都不能用,用完放自己柜子里,→_→可是这些都是公用的。至于抢别人定的摇床也是正常操作,以至于他们带的本科生师弟也飞扬跋扈,在下午抢了一个博士师姐的电泳槽说他着急看结果,师姐生气说着急为什么不中午看才立马道歉。两口子的厚脸皮程度就连大师兄也要退让三分,更何况他们还会在大组会上怼大老板自己的导师你敢信?导师给提意见会打断说自己知道。


不过两口子的实验能力有目共睹,师姐洗瓶子要洗到没有肉眼可见的一点点污渍反复清洗十几遍不聚成水滴也不成股流下,这一点是我们做不到的。所以两口子实验效率特别高。


作者:时问桫椤
来源:mdnice.com/writing/d841b81020b94d57821fa484883a2e14
收起阅读 »

《青春咖啡馆》书籍推介

《青春咖啡馆》书籍推介 摘要 一些书籍的阅读往往能带来自我心灵的疗愈,《青春咖啡馆》就是这样的一本书,书中描写了一个和20岁左右的女孩子关于心中幸福的追索,反映出那个年代探索人生意义的青年群像。20世纪60年代,法国存在主义兴起,青年在这些思...
继续阅读 »

《青春咖啡馆》书籍推介





摘要


一些书籍的阅读往往能带来自我心灵的疗愈,《青春咖啡馆》就是这样的一本书,书中描写了一个和20岁左右的女孩子关于心中幸福的追索,反映出那个年代探索人生意义的青年群像。20世纪60年代,法国存在主义兴起,青年在这些思潮的引导下渴望摆脱人生的束缚,不断逃离那些既定的轨道,在“去存在”中获得自由。可是,一味地追求“存在”、“自由”,真的可能吗?故事的女主人公就是如此,她最后选择存在于另一个世界……


点评


《青春咖啡馆》是莫迪亚诺最令人心碎的作品之一。作品一如既往地充满了调查与跟踪,回忆与求证,找不到答案的疑问。“您找到您的幸福吗?”可是,露姬到哪里去寻找她的幸福呢?咖啡馆?书籍?大街上的游荡?婚姻中?逃跑?她全试过了,包括毒品和神秘学,可她像其他许许多多的人一样,最终消失在时间的长河中。


历史背景


本书的故事发生在20世纪60年代的法国巴黎,正是各种青年学生运动盛行的时期。当时有一位重要的思想家居伊·德波,他的思想曾对1968年的法国青年学生运动“五月风暴”产生过巨大影响。本书的作者莫迪亚诺也引用了他的这样一句话放在小说开头:



在真实生活之旅的中途,


我们被一缕绵长的愁绪包围,


在挥霍青春的咖啡馆里,


愁绪从那么多戏谑的和伤感的话语中流露出来。 ——居伊·德波



国际情景主义者认为,“在这个被商品和景观统治的社会中,创造精神和人生梦想失去了自己的家园,人生活在这样的环境里感到窒息”,所以他们主张用创造生活取代“被动生活”,呼吁“毫无拘束地生活、毫无节制地享受”和游戏人生,并进行人生的“漂移” (dérive)。居伊·德波在《漂移理论》一书中指出,漂移是“一种快速通过各种环境的技巧”,是指对物化的城市生活,特别是建筑空间布局的凝固性的否定。《青春咖啡馆》的故事发生在六十年代初,正是情景主义者活动最如火如荼的时期。作品中的人物似乎都在按照情景主义者的规则生活着,跟那些情景主义者一样,他们都认为工作和学习是束缚人的,“永远也别工作”,写在墙上的标语非常醒目。


小说结构


这部小说以上世纪六十年代的巴黎为背景,巴黎塞纳河左岸的拉丁区,一家名叫孔岱的咖啡馆,吸引了一批年轻人。他们四处漂泊,居无定所,放荡不羁,过着今朝有酒今朝醉的生活,他们之中有作家、艺术家、大学生,他们沉湎于酒精和毒品。故事就从他们当中一个名叫露姬的女子出现、失踪、追忆到后来她自杀的过程来展开故事的。整个故事并不完全是以线性方式展开,而是通过四个人的视角来讲述一个相互交叉的故事。读完这本书,我有一个疑问,这种叙述方式是否已经成为当代文学的一种常态,福克纳、略萨的作品都用了这种方式。


叙述者一(巴黎高等矿业学院的学生)


第一个叙述者是一名巴黎高等矿业学院的学生,他也是孔岱咖啡馆的常客,通过他的视角我们第一次见到本文的女主角,“露姬”这个名字也是他给取的。他还带领我们参与了咖啡馆的日常,认识了咖啡馆的服务生和客人,其中一个人称“船长”的客人连续三年记录了咖啡馆客人到达的时间和他们的住址,“船长”离开巴黎时将记录的笔记本留个了这位讲述者,他不断的翻阅笔记本,露姬在他的追寻下,一步一步的清晰起来。露姬是一个蓝眼睛,棕色头发,指甲修长的美女。她身体笔直,形态优雅,一言不发,谨小慎微,手里经常拿着一本《消失的地平线》,与咖啡馆的其他人格格不入。叙述者因此断定“她到孔岱这里,是来避难的,仿佛她想躲避什么东西,想从一个危险中逃脱。”这是从一个陌生人的角度对女主角的描述。


叙述者二(盖世里,一名私家侦探)


第二个叙述者名叫盖世里,是一名私家侦探。他讲述了一个名叫让-皮埃尔·舒罗的人,委托他寻找舒罗离家出走几个月的妻子雅克林娜,据舒罗说,他是在自己的房地产公司结识雅克林娜的,她是他的秘书,为了“建立关系”,他们二人结婚,婚后雅克林娜觉得丈夫无趣,狠心离家出走。盖世里很快查明雅克林娜的真实身份,她二战时期出身于索洛涅,没有父亲,由母亲单独抚养,母亲在红磨坊当服务员。她幼年时,母亲上班时经常将她一人留在家里,她因孤单和恐惧,时常在母亲上班时外出闲逛,并沾染上毒品,两次因“未成年流浪”被警察抓走。在盖世里的深入调查下,雅克林娜就是露姬这一事实得以解开。随着了解的进行,盖世里被雅克林娜的经历打动,似乎理解了她离家出走的缘由,最后,放弃侦查,不再干扰她的生活。这是从一个侦探的角度让人物从模糊走向清晰的过程。


叙述者三(女主人公,本人)


第三个叙述者是露姬(雅克琳娜)本人。她讲述了她在十八区拉谢尔大道10号度过的童年和少年时光。晚上,她母亲上班不在家,她就偷偷溜出去闲逛。一次在九区,一次在十八区,一个男人和一个女人,为她提供了战胜恐惧的“良药”,她尝试吸毒,吸过之后她不再感到恐惧。在克里希林荫大道,她结识一家专门售卖科幻和天文学书籍的书店的老板,老板送了一本《无限之旅》的书给她,让她体验了阅读的乐趣。她解释了自己为什么总想逃走“每次我和什么人断绝往来,我都感到一种沉醉。”不管是年少时的离家出走,还是从丈夫家的逃离,都是居于这样的原因。这是从当事人角度的叙述,部分回答了第一叙述人和第二叙述人的疑惑,让谜一样的露姬逐渐的立体丰满起来。


叙述者四(罗兰,露姬的情人)


第四个叙述人是露姬的情人罗兰。罗兰是一个刚入门的作家。他与露姬在一个名叫居伊·德·威尔组织的聚会上认识,威尔是一个神秘学家,也是这群年轻人的精神导师,他推荐露姬阅读《消失的地平线》和《不存在的路易斯》。罗兰和露姬相识相爱,露姬不想光顾能勾起她痛苦回忆的拉丁区,十六区又离她丈夫家很近,他们因此生活在中立地区,但也并不感到安全,于是谋划出国旅游,还未成行,露姬突然跳窗自杀,故事戛然而止。


哲理


《青春咖啡馆》作者是2014年诺贝尔文学奖得主,他生活在法国,深受法国哲学思想的熏陶,他在这本书中大段引用了法国哲学家吉尔·德勒兹的“逃逸线“概念。


“逃逸线”(ligne de fuite)是法国哲学家德勒兹(1925-1995)经常使用的概念,在后期经典之作《千座高原》中,他详细区分了三种类型的“线”:坚硬线、柔软线和逃逸线。





  • 坚硬线指质量线,透过二元对立所构建僵化的常态,比如说人在坚硬线的控制下,就会循规蹈矩地完成人生的一个个阶段,从小学到大学到拿工资生活到退休。





  • 柔软线指分子线,搅乱了线性和常态,没有目的和意向。





  • 逃逸线完全脱离质量线,由破裂到断裂,主体则在难以控制的流变多样中称为碎片,这也是我们的解放之线,只有在这条线上我们才会感觉到自由,感觉到人生,但也是最危险之线,因为它们最真实。




故事的主人公露姬就是一个摆动在坚硬线和逃逸线之间的女孩子,她说:



后来,我每次与什么人断绝往来的时候,我都能重新体会到这种沉醉。只有在逃跑的时候,我才真的是我自己。我仅有的那些美好回忆都跟逃跑或者离家出走连在一起。但是,生活总会重新占据上风。当我走到迷雾街时,我深信有人约我在此见面,这对我来说又会是一个新的起点。(p82)



露姬的心理


一方面她渴望逃脱出坚硬线的束缚,追求自己认为的幸福,自己认为的“真正的生活”,每当她逃离的时候,她都会感到一种沉醉、自由。另一方面,她不断逃跑,但是后来生活总会占据上风,这是一个从“逃逸线”回归“坚硬线”的过程。


从她的逃跑经历来看,在露姬十三四岁的时候,她母亲上班要上到凌晨两点,于是露姬喜欢一个人在半夜出门,在大街上走来走去。这导致她曾两次因未成年流浪被警察叔叔送回了家,这就是她最开始体会到,她离家出走后生活总会重新占据上风,她又会进入一个有明确意义的事件中。


之后她母亲去世,露姬与一个名叫舒罗的受过良好教育的中产结婚了,她的结婚又是一种对“坚硬线”的回归。



可她为什么要嫁给舒罗?结婚之后再次出逃,但这一次却是朝左岸逃,就好像过河之后,她就逃脱了迫在眉睫的危险,并得到了保护。可是,这桩婚姻对她来说不也是一种保护吗?假如她有足够的耐心呆在诺伊利,久而久之,人们就会忘记在让-皮埃尔·舒罗夫人的底下还藏着一个雅克林娜·德朗克。(p53)



露姬不断逃离,不断融入新的关系之中,“他们只是尝试建立关系”。露姬总是在逃离那个幸福不在的地方,但当她到了一个新的地方,她又觉得幸福不在那里。



她说,真正的生活,不是这样的。可当他问她那种“真正的生活”到底是什么样子时,她就一直耸肩膀,不置一词,就好像说了也是白说。(p39)



结合拉康精神分析


可以说,露姬是一个在不断逃离大他者和小他者的女孩子。她在逃离那些社会规范,比如家庭、婚姻、学校,即所谓的大他者。她也在逃离他人的想象,比如她尝试与她原来在酒吧的那些朋友绝交。



我的心中充满了沉醉的感觉,这种沉醉是酒精或者那雪什么的永远给不了的。我往上一直走到迷雾城堡。我已经痛下决心永远也不和康特尔酒吧里的那帮人见面了。



她希望逃离一切束缚,但是她根本没有意识到她无法逃离大他者和小他者,她从家庭逃到婚姻再逃到友情、爱情,永远都有一个大他者存在。同时,她伪造自己的真实身份,骗别人说自己是学习东方语言的大学生,说自己母亲是会计师。她认为在社会中,“学习东方语言的大学生”似乎比中学辍学更加体面,会计师比红磨坊夜总会的服务员更加体面。她始终没有逃离那个大他者带给她的评价标准,那个无处不在的大他者。因此,她的逃离最终必然以失败告终,也正是如此,最后露姬选择以跳楼自杀的方式,逃离那个无处不在的重力,逃离这个无处可逃的世界。


那么,您找到您的幸福了吗?


这句话贯穿了全书,最开始是书店老板莫名奇妙地一句话,这句话深深地印在露姬的脑海里。



有人言之凿凿地告诉我:人唯一想不起的东西就是人说话的嗓音。可是,直到今天,在那些辗转难眠的夜晚,我却经常能听见那夹带巴黎口音——住在斜坡街上的巴黎人——的声音问我:“那么,您找到您的幸福了吗?”



译后记·四


这本书的译者是金龙格先生,他在译后记中这样分析“那么,您找到您的幸福了吗?”这句话。


《青春咖啡馆》以一种既写实又神秘的笔调,交织谱出青春岁月的青涩、惶惑、焦虑、孤独寂寞与莫名愁绪,描写一个弱女子从不断探寻人生真谛到最终放弃生命追寻的悲剧命运,这个悲剧发生在一个既有着迷人的魅力又像谜一样难以捉摸的年轻美丽女子身上,更使全书充满一种挥之不去的忧伤情调。书中的一句问话像哲学命题一样尤其发人深省:“您找到了您的幸福吗?”,可是,人能找到自己的幸福吗?人终其一生到底能够得到什么?小说中的主人公什么都尝试过了,最终却一无所获。莫迪亚诺的小说似乎在告诉我们,幸福只是昙花一现的东西,人生寻寻觅觅,到头来得到的只有落寞、失去、不幸、迷茫,只有时时袭来的危机与恐慌,只有萍踪不定的漂泊,只有处在时代大潮中身不由己的无奈和顾影自怜的悲哀。


总结


《青春咖啡馆》的法语原文是Dans le café de la jeunesse perdue,意思是“在咖啡馆里青春消逝”,作者以一种伤感的笔调描述了露姬消逝的青春,但是在我们的一生中,青春虽然过去了,但并不会消逝,它只会永远的封存在我们的记忆之中。


在我们的青春年代,或许学业、社会的压力,父母、老师的规训让我们也有点想要逃离,去追寻自己所认为的幸福所在。虽然露姬生活在20世纪60年代,但其实人们的心底或多或少都有露姬的影子,就比如那个巴黎高等矿业学校的大学生、侦探盖世里、情人罗兰,包括你我。我们或许向往着那种不断逃离的生活,这就是当时情景主义者的生活,但作者并没有站在道德制高点对这种生活做出评判,只是如实进行记录,让读者跟着他的笔触,去认识去感受曾经有那样一群人、一个人这样生活过。探讨人生价值的文学作品屡见不鲜,网络发达的今天,许多人也会在网上总结、抱怨、指导、感悟人生的意义,不同的人会有不同的答案,这个答案不可能统一,也没有必要统一,千差万别的人生才是真正的人生。


作者:yueyh
来源:mdnice.com/writing/e894ad0fefa54767a64e22f5a7ac50ff
收起阅读 »

回县城躺平,感觉我的人生过得好失败

从春节前到现在,一个半月没更新了,做啥都提不起劲来。 越来越感觉我的人生过的好失败。 去年我爸因为癌症去世了,家里的门头房用不到了,就想卖掉,找好了买家,价格谈了 140 万。 当时想买我们这个房子的人很多,那个买家怕我们卖给别人,就拿了 20 万定金,和我们...
继续阅读 »

从春节前到现在,一个半月没更新了,做啥都提不起劲来。


越来越感觉我的人生过的好失败。


去年我爸因为癌症去世了,家里的门头房用不到了,就想卖掉,找好了买家,价格谈了 140 万。


当时想买我们这个房子的人很多,那个买家怕我们卖给别人,就拿了 20 万定金,和我们签了一个买房合同。


没想到因为这个房子因为在我爸名下,涉及到继承,需要我奶奶放弃继承才可以过户。


我奶奶现在生活不能自理,由我大娘二大娘养着,然后他们提出条件来,要我们的宅基地,也就是村里的老房子。


我妈开始不同意,因为她想之后从那里出殡,和我爸合葬。


后来也同意了,在哪不能殡出去呢?


然后我这边准备好了材料之后,我堂姐跳了出来,一拍桌说,不行,老房子我们也要,另外你还要给我们 25 万。


她们说咨询了律师要是打官司的话,我们青岛的房子也要分,那个门头房也要分,另外我爸的银行流水也要查,起码得分她们 40 万。


我给讲价到了 20 万,但是我妈不同意,说是她和我爸辛苦攒下的家业凭什么白给他们。


我妈这边也找了律师,给出的意见就是拖着就行,一辈子不卖了。


这时候买房子的不干了,说是合同上写了,如果违约,要双倍返回定金,也就是赔她们 20 万。


当时我们以为就是个收到条就签了,没想到在这等着呢。


其实我们早就把定金返给她了,也说了我们家的情况,但她就是不行。


年前就一直威胁我们要告,刚过完年,马上又来了:



我妈问了下和谈的话怎么谈,她说起诉你赔我 25 万,和谈赔我 18 万。



两头挤我们,家里就要我们老房子 + 21 万,卖房子的就要我们 20 万违约金。


我们夹在中间,几度濒临崩溃。


我想了下,这件事早晚得解决,反正都是一家人,给家里人点钱也没啥。


然后我前几天去找我大爷二大爷,还有堂姐、堂哥坐在一起谈了,我说我同意这 21 万。


最终转了她们 18 万(老房子折合了 2 万块),然后又拿了 1 万律师费(他们请的律师让我拿律师费),还有同意给他们老房子。


但我提的要求是和我妈只能说是 10 万 + 老房子,不然我妈不会同意的。


就这样,我们顺利公证过了户。


公证放弃继承那天,我奶奶才刚知道这个事,她说她只要老房子,不要我爸的其他遗产。


但没办法,她不要不行,我大爷二大爷要啊。


这个房子卖了,到手 120 万。


然后还有青岛的房子,这个房子我买的时候是 70万首付 + 100 万贷款,一共是 200 万下来的,最近我妈又花了 7 万装修。


因为不去青岛住,也打算卖了,中介说价格不到 80 万还是可以卖掉的。



这么一算,这边亏了 120 万,那边房子卖了剩下 120,相当于我爸就给我留下了 70 多万还不好卖的房子。


其实我爸这辈子攒了不少钱,差不多 300 万,都是省出来的,从小我跟着他就是一天吃一顿那种,从没感觉到家里是有钱的。


再就是他对我妈也不好,前几年的时候经常打骂,后来我妈离家出走了,但是他生病了还是会来照顾他。


我爸癌症住院那段时间,生活不能自理,都是我妈没日没夜的照顾他。


临走之前,我爸一只手抓着我的手,一只手抓着我妈的手,然后让我们好好相处,他一直觉得对不起我妈,口里一直喊着“从头再来、从头再来”。


我送我爸去火葬场的时候,送我骨灰盒爸入土的时候,我也一直在说,“爸,你别怕,我们从头再来”。


其实我爸葬礼上,我没有咋哭出来,可能当时没大反应过来。


但是之后好长一段时间,我在村里别人家坐着聊天,一谈起我爸,就再也忍不住了,哭的稀里哗啦的。


我有个干兄弟,在村里拜了干爹,因为疫情好多年也没走动了,但是我爸的棺材是他帮忙抬出去的。


而我大爷二大爷就在一边看着。


我今年过年给他家送了礼,我说,我妈说我爸是你们抬出去的,让我一辈子记得你们的好。


当时说到这里,没忍住,又哭的稀里哗啦的。


我想我爸这辈子,是攒了不少钱,但是不舍得吃不舍得喝的,还在房子上亏了半辈子的积蓄。


对老婆孩子不好,临走前才后悔想着从头再来。


我想我前五年是赚了不少钱,但因为工作,好多年没回家,和家人一年待在一起也就几天。


而且最后都赔在青岛的房子上了。


人这一辈子,到底图啥呢?


年后这几周我找了找工作,有几个不错的 offer,都是 base 40+ 那种。



但我又不那么想出去了。


我这一年没工作,其实和我妈在一块生活还是很踏实的。


而且家里房子卖了,青岛的房子也快了,这样我的存款差不多能到 300w。存定期的话每年银行利息 8w 左右,够我生活了。


就这样在家躺平一辈子是不是也不错。


王小波说,那一天我二十一岁,在我一生的黄金时代,我有好多奢望。我想爱,想吃,还想在一瞬间变成天上半明半暗的云,后来我才知道,生活就是个缓慢受锤的过程,人一天天老下去,奢望也一天天消逝,最后变得像挨了锤的牛一样。可是我过二十一岁生日时没有预见到这一点。我觉得自己会永远生猛下去,什么也锤不了我。


韩寒说,平凡才是唯一的答案。


小的时候,我希望长大后的自己会光芒万丈。


长大以后,我希望自己有个好的工作打工到退休。


现在的我只想躺平。


我觉得我自己的人生很失败:


打工这些年,钱都赔在房子上了。


我比较社恐,永远达不到我妈对我的会来事、会察言观色的期望。


人家都在大城市结婚生子、买房定居了,而我又回到了小县城。


当年和我同时入职高德的朋友都升 p7 了,我现在啥也不是:



我是 94 年的,今年就 30 了,人生的各种机会和可能性越来越少。


后半辈子,我应该就是在小县城躺平,度过余生了。


但文章我还是想继续写,毕竟人这一生总要坚持点什么。


作者:zxg_神说要有光
来源:juejin.cn/post/7343503718183059471
收起阅读 »

年会结束,立马辞职了!

那是发生在多年前的一件事,当时我也是在那家公司做 Java 开发。公司很大,大到去了很长一段时间都感觉毫无存在感。 那年年会,作为技术部的我,依然被安排到一个比较边缘化的桌子,这么多年走来,早已经习惯了这样的安排。 可能只有我们做技术人的心里才会觉得“技术...
继续阅读 »

那是发生在多年前的一件事,当时我也是在那家公司做 Java 开发。公司很大,大到去了很长一段时间都感觉毫无存在感。


那年年会,作为技术部的我,依然被安排到一个比较边缘化的桌子,这么多年走来,早已经习惯了这样的安排。


可能只有我们做技术人的心里才会觉得“技术牛逼,技术万岁!”,但在公司领导层看来,这技术研发部就是整个公司开销最大的一个部门,又不能直接产生效益,但开除了又不合适,还要靠他们干活呢,这真是一件即讽刺、又无奈的事儿啊。


说回正题,那年公司所有人依旧是尴尬的、极不情愿的、又不得不碍于情面凑在一起,听完了所谓的又毫无意义的年终总结,然后又敷衍的敬完酒之后,才能装模作样的挥手告别亲爱的同事。


我之所以,要等待年会的第二天才告诉我的顶头上司“我要离职”的主要原因是,年会的时候才给大家集中发年终奖。


我也是领到钱之后就不装了,我摊牌了,第二天就找到了领导,告诉他,我要离职了。这个时候上司也知道你的心思,话已经收出来了,尤其是离职的事,大概率是劝不回来了,毕竟覆水难收。大家都是明白人,寒暄了几句之后,就签了离职的申请。


工作就像谈对象,合不来也没必要勉强。那时候开发的行情还很好,出去面试 4 家公司,最少也能拿 3 个 Offer,所以跳槽基本都是裸跳,一副此地不留爷,自有留爷处的傲娇姿态。


然而,年终奖是拿到手了,新工作也很快又着落了,薪资每次跳槽也能涨到自己满意的数,但干着干着发现,好像还是原来的配方,还是原来的味道,好像也不是理想中的工作嘛。


于是,在周而复始的折腾中才发现,只要是给别人上班,永远不会有理想中的工作,因为上班的本质是你替别人办事,别人给你发薪水,工作从来都是简单的雇佣关系,那来的别人要为你的理想来买单嘛,这本来就不合理,只是想明白这点时,以是上班了十年之后(此处可见自己的笨拙)。


理解了这点之后,我才发现,给任何公司上班的区别不会太大,无非是钱多钱少、活多活少、周围人好相处与否的细微差别,但碍于生计,又不得不苟延残喘的上下班,这可能是大部分打工人的真实感受和现状了。


但即使这样,你依然会发现,你的岗位正在被新人所替代,你的选择也变的越来越少,你的挣钱能力也变的越来越弱,这可能就是所谓的“中年危机”吧。所以说“中年危机”这个词,不是那个行业的专属名称,而是所有行业共性,那要怎么解决呢?


三个小小的建议:




  1. 尽量不要买房:不要和自己过不去,买房一时爽,还贷“火葬场”。我有一个朋友,一个月 2.1W 的房贷,生活中哪怕有一点点小小的变动,对于他来说都是不可承受之殇。“如履薄冰”也不过如此吧?


  2. 培养自己的第二职业:找到自己感兴趣点,并且它能帮你长久的带来经济收益最好,不求大富大贵,只要能够日常开支已经很不错了。任何时候有准备都比没准备要强很多。还有,在做之前,不要怕起步晚、进步慢,只要肯坚持,终会有收获。路虽远,行则将至;事虽难,做则必成。


  3. 提升自己主业的能力:任何时候,提升自己主业的能力,都是收益最大的投资,也是最明智的投资,当你看不清前进的道路时,当你感觉人生黯淡无光事,唯有干好自己目前本职的工作,才是最优的选择,这也能让你为以后的新计划积攒足够的能量。


最后,愿新的一年里:奔赴热爱、享受自由,找到自己热爱的事,并为之努力。加油,XDM~


作者:王磊
来源:mdnice.com/writing/728744844d414145b2efa61ec218606c
收起阅读 »

产品经理的多维度划分

产品经理的进阶是一个涉及专业技能提升、经验积累、视野拓宽以及领导力培养的过程。一.产品经理的层次划分以下是一些产品经理进阶的关键步骤和能力要求:初级产品经理阶段:需求细化与执行:学会撰写高质量的产品需求文档(PRD)、绘制产品原型,具备基本的设计理解和一定的技...
继续阅读 »

产品经理的进阶是一个涉及专业技能提升、经验积累、视野拓宽以及领导力培养的过程。

一.产品经理的层次划分

以下是一些产品经理进阶的关键步骤和能力要求:

  1. 初级产品经理阶段

    • 需求细化与执行:学会撰写高质量的产品需求文档(PRD)、绘制产品原型,具备基本的设计理解和一定的技术背景知识,能够准确传达并跟进需求的执行。
    • 沟通协作:与开发、设计、运营等部门紧密合作,确保需求被正确理解和实施。
    • 基础技能:掌握需求分析、文档编写、原型设计工具使用、基本的用户研究和竞品分析。
  2. 中级产品经理阶段

    • 主动挖掘与项目管理:具备独立进行用户研究、数据分析、竞品分析的能力,主动寻找和验证市场需求,制定并执行产品策略。
    • 产品决策:开始涉及产品方向的选择与功能优化的取舍,具有更全面的产品视角和全局观。
    • 项目管理:有效管理产品生命周期中的各个阶段,保证项目的进度和质量。
  3. 高级产品经理或产品专家阶段

    • 战略规划:负责产品体系的整体规划,形成独特的产品方法论,能够预见和引领行业趋势。
    • 领导力:带领产品团队,负责整个产品线的战略布局和生命周期管理,影响团队成员成长和决策。
    • 成功案例与影响力:拥有成功的产品案例,能通过实践提炼出可复制的产品模式和最佳实践,对外输出方法论和思想领导力。
  4. 管理线进阶

    • 团队建设:组建和管理高效的产品团队,培养人才梯队,进行有效的团队激励和绩效管理。
    • 业务拓展:推动产品商业化进程,对市场反馈敏感,根据市场变化调整产品战略。
  5. 专业线深化

    • 领域专家:在某一细分领域成为专家,深入研究行业规则和技术发展趋势,指导复杂产品解决方案的构建。

此外,产品经理在进阶过程中还需要不断学习和适应新技术、新商业模式的变化,持续提升跨部门协调、解决问题、创新思维和决策能力。同时,良好的自我管理和情绪智商同样是职业发展中不可忽视的素质。随着职位的提升,产品经理可能面临更多战略层面的问题,因此需要不断提升自身的商业洞察力和战略规划能力。

二.高级产品经理能力模型

高级产品经理的能力模型通常涵盖了以下几个关键领域:

  1. 战略思维能力

    • 深入理解行业发展趋势,能够制定长远的产品发展战略和路线图。
    • 能够结合公司整体战略目标,明确产品定位,设定并达成有挑战性的产品愿景和目标。
  2. 用户洞察与需求提炼

    • 具备深入的用户研究和洞察力,能精准把握用户痛点与需求,并转化为产品特性。
    • 利用数据分析手段,量化用户行为,驱动产品迭代优化。
  3. 数据驱动决策

    • 强大的数据解读和分析能力,利用A/B测试、用户行为数据等工具,以数据为基础做出科学决策。
    • 能够建立和完善数据指标体系,用于衡量产品性能和市场表现。
  4. 跨部门协同与领导力

    • 出色的团队管理和组织协调能力,能有效调动内外部资源,推动跨职能团队合作。
    • 具备卓越的领导魅力,激发团队潜能,带领团队完成复杂项目。
  5. 创新与解决问题能力

    • 在面对复杂问题时,能够提出创新解决方案,突破现有框架,引领产品创新。
    • 对技术和市场变化保持敏锐度,预见并应对潜在的竞争威胁和市场机会。
  6. 专业技术能力

    • 深厚的产品设计理论基础,熟练掌握产品生命周期管理、敏捷开发流程等专业技能。
    • 能够深入参与产品设计和技术实现细节,与工程师团队有效沟通。
  7. 商业敏感性与财务知识

    • 具备较强的商业头脑,能从经济和盈利角度考虑产品发展,平衡用户价值与商业价值。
    • 了解财务模型和成本效益分析,能够在产品设计中合理权衡投入产出。

综上所述,高级产品经理不仅需要具备扎实的产品设计和管理能力,还需要有很强的跨领域整合能力、领导力以及对市场、技术、用户和商业的深刻理解,从而成功引领产品的长期发展和市场竞争。

三.产品经理的多维分类

产品经理的角色可以根据多个维度进行分类,以下是几个主要分类方式及其具体类型:

1. 按照服务对象划分:

  • B端产品经理 (Business-to-Business, B2B):主要负责为企业级客户提供产品和服务,例如企业软件、SaaS解决方案、云服务、后台系统等,这类产品经理需要深入理解客户业务流程,解决企业级痛点,注重产品的易用性和效率提升。

  • C端产品经理 (Business-to-Consumer, B2C):专注于为消费者打造产品,这涵盖各种消费级应用、网站、游戏、电商产品等,要求产品经理深入了解用户需求、偏好及行为模式,提供优秀的用户体验。

  • G端产品经理(Business-to-Government, B2G):G端产品经理是指专为政-府机构服务的产品经理,他们聚焦于政务信息化领域,负责设计、优化和管理面向政-府内部或公众的政务类数字产品。核心任务包括:依据政-府业务需求定制信息化解决方案,如搭建行政审批、公-文处理等内部管理系统;开发一站式便民政-务服务产品,如政-务服务网、政-务APP等,实现政-策查询、在线办理等功能

2. 按前后端划分:

  • 前端产品经理:专注于用户界面和交互设计,确保用户能够直观地使用产品,关注用户体验的全流程,包括UI/UX设计、页面跳转逻辑、信息展示结构等。

  • 后端产品经理:主要关注产品后台系统的设计和维护,包括但不限于数据存储、服务器架构、API接口设计、性能优化等非用户直觉感知的功能部分。

  • 中台产品经理:主要负责设计和规划公司的业务中台产品,确保中台系统的稳定、高效运行,并赋能前台业务快速发展。业务中台作为一种重要的IT架构模式,旨在沉淀和复用企业的核心能力,如用户中心、订单中心、商品中心等,为多个前台业务提供通用、灵活且可配置的服务。

3. 按照职能分类:

  • 功能型产品经理:主要职责是设计和优化产品功能,确保功能满足用户需求和业务目标。

  • 战略型产品经理:负责产品整体战略规划,确定产品定位、发展方向,以及基于市场分析、竞争态势作出前瞻性决策。

  • 运营型产品经理:侧重于产品与运营相结合,将运营策略转化为产品功能,关注用户增长、活跃度、留存等运营指标的提升。

  • 数据驱动产品经理:利用数据驱动产品优化和决策,熟悉数据分析工具,能从海量数据中发现规律并指导产品迭代。

  • AI/算法产品经理:在AI、大数据等领域,负责设计和优化基于算法和模型驱动的产品功能。

4. 按照行业分类:

  1. 电子商务产品经理
    • 负责电商平台的产品规划和优化,比如淘宝、京东等综合电商平台的商品管理、订单系统、支付系统、物流跟踪等模块,以及垂直细分市场的电商解决方案。
  2. 社交网络产品经理
    • 主要负责社交产品如微信、微博、QQ等的策划与迭代,关注社交互动、社区运营、信息传播、用户关系链构建等。
  3. 金融产品经理
    • 设计和优化金融服务产品,包括银行应用、证券交易平台、金融科技产品(如P2P借贷、众筹平台、区块链应用)、支付工具等,涉及资金流转、风险管理、合规要求等内容。
  4. 教育科技产品经理
    • 开发在线教育平台、教育管理软件、智慧校园系统等,关注课程设计、学习路径规划、教学资源管理等功能。
  5. 健康医疗产品经理
    • 专注医疗健康管理、电子病历系统、远程诊疗平台、智能穿戴设备配合的健康管理APP等产品的研发,需对接医疗资源、遵循医疗规范和隐私保护法规。
  6. 游戏产品经理
    • 负责游戏产品的策划、更新、运营,关注游戏玩法设计、用户体验、付费模型、社交元素等。
  7. 企业服务(B2B)产品经理
    • 包括CRM、ERP、HRM、SCM等各种企业管理软件,以及云服务、大数据分析工具等,需了解企业运营流程并提供针对性的解决方案。
  8. 物联网(IoT)产品经理
    • 负责智能家居、智能城市、工业自动化等领域的软硬件一体化产品设计,涉及传感器、智能设备、数据分析平台等。
  9. 媒体娱乐产品经理
    • 从事视频流媒体平台、音乐播放器、新闻资讯App等产品设计,关注内容分发、版权管理、个性化推荐等功能。
  10. 人工智能(AI)产品经理
    • 专门从事AI产品如智能语音助手、图像识别系统、自动驾驶系统等的研发,需理解机器学习原理、数据训练过程并转化为用户友好的产品形态。

5. 按照层级划分:

  • 初级产品经理:通常负责较具体模块或任务,配合上级完成产品设计与迭代。
  • 中级产品经理:可以独立承担某个产品线或子产品的规划与执行。
  • 高级产品经理乃至产品总监:负责整个产品部门或多个产品线的战略规划与执行,具备较强的战略眼光和团队管理能力。

6. 按照产品领域分类:

  • 软件产品经理:负责软件产品的规划、设计和管理。
  • 硬件产品经理:专注于硬件产品的开发和推广。
  • 互联网产品经理:管理互联网产品,如网站、移动应用等。
  • 电商产品经理:负责电商平台或相关产品的策划和运营。

以上分类并不绝对孤立,实际工作中产品经理的角色可能会结合多种分类特征,且随着行业的发展和市场需求的变化,还会出现新的产品经理角色类型。


作者:西边一山
来源:mdnice.com/writing/f1f3d57fedef4800932a6afd643809f1

收起阅读 »

需求分析

产品经理在进行需求分析时,首先需要明确需求分析的目的和重要性,即从用户需求出发,挖掘用户的真正目标,并转化为产品需求的过程。接下来,可以通过以下文了解如何来做好需求分析。image-202403070006130051.什么是需求分析需求分析也称为软件需求分析...
继续阅读 »

产品经理在进行需求分析时,首先需要明确需求分析的目的和重要性,即从用户需求出发,挖掘用户的真正目标,并转化为产品需求的过程。接下来,可以通过以下文了解如何来做好需求分析。

image-20240307000613005
image-20240307000613005

1.什么是需求分析

需求分析也称为软件需求分析、系统需求分析或需求分析工程等,是开发人员经过深入细致的调研和分析,准确理解用户和项目的功能、性能、可靠性等具体要求,将用户非形式的需求表述转化为完整的需求定义,从而确定系统必须做什么的过程。

需求分析是软件计划阶段的重要活动,也是软件生存周期中的一个重要环节,该阶段是分析系统在功能上需要“实现什么”,而不是考虑如何去“实现”。需求分析的目标是把用户对待开发软件提出的“要求”或“需要”进行分析与整理,确认后形成描述完整、清晰与规范的文档,确定软件需要实现哪些功能,完成哪些工作。此外,软件的一些非功能性需求(如软件性能、可靠性、响应时间、可扩展性等),软件设计的约束条件,运行时与其他软件的关系等也是软件需求分析的目标。

2.需求分析的重要性

需求分析指的是在建立一个新的或改变一个现存的产品时,确定新产品的目的、范围、定义和功能时所要做的所有工作。这个过程通常涉及多个部门和团队成员,包括产品经理、设计师、开发者、销售团队和潜在用户。产品需求分析的目的是确保产品满足市场的需求,为用户提供价值,并与公司的战略目标和愿景保持一致。

img
img

需求分析的重要性在于:

  • 确保产品方向正确:帮助团队确定正确的产品方向,避免开发与市场和用户需求不符的产品。
  • 提高资源利用效率:需求分析能够明确需求,而明确的需求可以帮助团队更加高效地分配资源,避免浪费时间和资金在不必要或优先级较低的功能上。
  • 降低项目风险:需求分析需要我们去深入了解用户需求和市场趋势,所以它可以帮助团队识别潜在的风险,并提前采取措施来应对。

除此以外,需求分析还能够起到提高产品质量加强团队沟通提高用户满意度等等。

3.需求分析的时机

  • 产品规划阶段:在确定产品方向和目标时,进行需求分析以了解市场和用户需求。
  • 产品设计阶段:在设计产品功能和界面时,根据需求分析结果进行具体的设计。
  • 产品迭代阶段:在产品上线后,根据用户反馈和市场变化,持续进行需求分析以优化产品。

需求分析贯穿整个产品生命周期,但尤其重要的是在项目启动阶段和迭代更新时进行。在项目开始前进行全面的需求分析;在产品上线后根据用户反馈和市场变化不断调整优化需求。

4.需求分析的方法

4.1需求分析的最佳实践和方法论

主要包括以下几个方面:

  1. 业务分析而非系统实现:需求分析的任务不仅仅是分析系统如何实现用户的需要,而是更广泛的业务分析,这包括了对业务知识、问题列表等方面的定义。

  2. SERU框架:《软件需求最佳实践》一书中提倡的SERU框架是一套重要的需求分析方法论,它将目标系统分解为主题域,再分解为流程,最后得到用例以及业务实体。

  3. 需求定义和捕获:需求定义是需求分析的起点,涉及到从用户需求中提炼出产品需求的过程。需求捕获则是在此基础上进一步细化需求,确保需求的准确性和完整性。

  4. 需求分析与建模:在需求分析的第一阶段完成结构框架和行为脉络的梳理后,第二阶段的工作任务是填充需求的细节,即根据前面的框架进行需求细节的填充。

  5. 功能分解、结构化分析、信息建模、面向对象分析:需求分析的主要方法包括功能分解方法、结构化分析方法、信息建模方法以及面向对象的分析方法。这些方法有助于从不同角度深入理解和描述需求。

  6. 深入理解需求并调整认知:需求分析的本质是根据认知进行假设,然后给出判断。核心是不断深入理解需求,调整需求认知,让自己的假设尽可能贴近客观事实,以得出更加准确的判断。

需求分析的最佳实践和方法论是一个综合性的过程,涉及到业务分析、需求定义、捕获、分析与建模等多个环节。通过采用SERU框架等方法论,结合功能分解、结构化分析、信息建模、面向对象分析等方法,可以有效地进行需求分析和建模,从而确保软件开发项目能够满足用户的真实需求。

这里,以下对第5点进行简单阐述包括以下几点:1、功能分解方法;2、结构化分析方法;3、信息建模方法;4、面向对象的分析方法。功能分解方法是将新系统作为多功能模块进行组合。各功能亦可分解为若干子功能及接口,子功能再继续分解。

4.3 功能分解方法在需求分析中的具体步骤和技巧有哪些?

  1. 分解步骤:功能分解首先需要将复杂系统分解为更小、更简单的功能单元。这些步骤可以是具体的功能点,也可以是更抽象的操作流程或用户界面元素。例如,通过用户故事切分流程图来准备待切分的需求,或者通过功能分解法将业务功能和辅助功能分开。

  2. 分析技巧:在进行功能分解时,需要分析每个用例之间的约束关系、执行条件,并组织出各种业务流程图。这有助于清晰地理解每个功能单元之间的关系和相互作用。

  3. 评估与优化:在完成功能分解后,需要对分解后的功能单元进行评估,以确定哪些是核心需求,哪些是次要需求。根据评估结果,可能需要对需求进行进一步的调整和优化。

  4. 技术应用:功能分解方法不仅限于软件开发领域,它还可以应用于其他复杂系统的设计、分析和实现过程中。通过对系统功能的分解,可以简化设计和实现的复杂性,提高效率。

  5. 实践案例:在业务场景分析中,功能分解方法结合从场景到挑战再到方案的思考模型,可以有效完成分析过程,输出初步的解决方案。这种方法强调了从具体场景出发,逐步深入到问题挑战和解决方案的整个过程。

功能分解方法在需求分析中的应用涉及到分解步骤的制定、分析技巧的运用、评估与优化的过程,以及技术应用和实践案例的分享。这些步骤和技巧共同作用于需求分析的各个阶段,帮助团队更高效、准确地理解和满足用户的真实需求。

4.4结构化分析方法在识别关键需求时的有效性如何评估?

  1. 需求分析的重要性:首先,需要认识到对软件需求的深入理解是开发成功的前提和关键。这意味着在进行结构化分析时,必须确保需求分析的准确性和全面性。

  2. 结构化分析过程:结构化分析方法包括与用户沟通获取用户需求的方法、分析建模与规格说明、实体—关系图、数据流图、状态转换图等内容。这些过程有助于确保对需求的全面理解和准确描述。

  3. 图形工具的应用:结构化分析中常用的图形工具包括层次方框图、Warnier图和IPO图等。这些工具有助于清晰地展示需求之间的关系和逻辑结构。

  4. 需求结构化的目标:结构化的目标是在业务需求向代码开发转换时,建立一个数字化标准,统一表达方式。这样做可以减少信息损耗,提高开发效率。

  5. 系统分析师的角色:结构化分析方法假定系统分析师理解问题域的全部,并且有能力正确地识别和分解问题。这种方法通过一次性将系统的功能分解到位,有助于提高分析的深度和广度。

  6. 系统体系结构的有效性评估:虽然结构化分析方法主要用于软件需求分析,但其有效性也可以扩展到评估系统体系结构。这需要考虑业务需求、适应性、可靠性、安全性等多个方面。

  7. 结构化数据分析:对于数据分析而言,确立明确的目标和提出假设是进行有效分析的重要第一步。这同样适用于结构化分析,有助于明确分析的方向和目标。

  8. 功能模型、数据模型和行为模型的使用:结构化分析中通常采用软件的功能模型、数据模型和行为模型来建模用户需求。这种方法有助于更准确地捕捉用户需求。

  9. 从可行性研究阶段得到的数据流图出发:结构化分析方法从可行性研究阶段得到的数据流图为起点,有助于确保需求分析的合理性和有效性。

结构化分析方法在识别关键需求时的有效性可以通过需求分析的重要性、过程的完整性、图形工具的应用、需求结构化的目的、系统分析师的角色、系统体系结构的有效性评估、数据分析方法的应用以及功能模型和行为模型的使用等多个方面进行评估。

4.5 信息建模方法在需求分析中的应用

它从数据角度对现实世界建立模型。大型软件较复杂;很难直接对其分析和设计,常借助模型。模型是开发中常用工具,系统包括数据处理、事务管理和决策支持。实质上,也可看成由一系列有序模型构成,其有序模型通常为功能模型、信息模型、数据模型、控制模型和决策模型。有序是指这些模型是分别在系统的不同开发阶段及开发层次一同建立的。建立系统常用的基本工具是E—R图。经过改进后称为信息建模法,后来又发展为语义数据建模方法,并引入了许多面向对象的特点。 信息建模可定义为实体或对象、属性、关系、父类型/子类型和关联对象。此方法的核心概念是实体和关系,基本工具是E-R图,其基本要素由实体、属性和联系构成。该方法的基本策略是从现实中找出实体,然后再用属性进行描述。

4.6 面向对象的分析方法在需求分析中的使用

面向对象的分析方法的关键是识别问题域内的对象,分析它们之间的关系,并建立三类模型,即对象模型、动态模型和功能模型。面向对象主要考虑类或对象、结构与连接、继承和封装、消息通信,只表示面向对象的分析中几项最重要特征。类的对象是对问题域中事物的完整映射,包括事物的数据特征(即属性)和行为特征(即服务)。

5.需求管理

5.1如何有效地进行需求管理以避免项目延误和资源浪费?

  1. 建立综合性需求框架:这是精细化管理的基础,有助于统一和明确需求的范围、质量要求等关键信息。

  2. 采纳迭代式需求优化:需求不是一成不变的,通过迭代优化可以更快地响应市场变化和用户反馈,同时也能减少因需求不明确而导致的项目延误。

  3. 运用数据分析提高预测准确性:利用数据分析工具来预测项目完成所需的时间和资源,可以帮助管理者合理规划项目进度,减少不必要的等待和返工。

  4. 构建跨部门沟通机制:良好的沟通是需求管理成功的关键。跨部门之间的有效沟通可以确保信息的准确传递,避免误解和重复工作,从而提高工作效率。

  5. 维护产品需求变更的历史记录:对于不断产生的新需求,需要有一个清晰的需求变更历史记录,以便追踪每一次需求变更的原因、影响以及解决方案,确保需求管理的准确性和一致性。

  6. 使用资源管理工具:通过资源管理工具,确保资源的分配与项目的优先级和实际需求相匹配,避免资源的过度分配和浪费,同时也能及时发现资源分配中的问题并进行调整。

  7. 实施版本控制与管理策略:有效实施版本控制可以帮助团队更好地管理需求变更,确保需求文档的准确性和一致性,降低沟通成本和避免冲突。

  8. 区分需求类别并制定优先级规则:在制定优先级规则之前,需要先区分需求类别,并根据“产品管理权”和“需求确定性”来划分需求类型,以确保资源的有效分配。

通过上述步骤,可以有效地进行需求管理,避免项目延误和资源浪费,从而提高项目管理的效率和成功率。

5.2敏捷开发方法在需求分析中的应用及其效果如何?

敏捷开发方法在需求分析中的应用主要体现在其迭代、增量式的方法论上,强调团队成员的自我管理、面对变化时的快速适应能力,以及持续的沟通和协作。敏捷需求分析在需求时机与过程、文档要求、变更、参与者角色等方面与传统方法有所不同,能够更好地参与到项目的生命周期演进中。通过合理的需求收集、需求分析与细化、需求优先级排序和需求跟踪等方法,可以更好地管理和满足项目的需求,提高团队的开发效率和产品质量。

敏捷开发的效果表现在多个方面。首先,敏捷指标的引入为软件开发生命周期中的不同阶段提供了对生产力的洞察,有助于评估产品质量并跟踪、优化团队绩效。其次,敏捷实践可以量化分析多种效能指标,如工作效率、可预测性、质量和响应程度等,这些指标有助于团队和项目管理者了解敏捷实践的实际效果。此外,敏捷开发中的过程度量指标,如业务指标和敏捷指标的跟踪,对于衡量开发过程的各个方面非常重要,这不仅侧重于解决方案是否满足市场需求,也包括衡量开发过程的各个方面。

敏捷开发方法在需求分析中的应用通过其独特的迭代和增量式方法论,结合合理的需求收集和管理方法,有效提升了团队的开发效率和产品质量,同时通过敏捷指标的应用,实现了对项目效能的全面评估和优化。

6.需求分析的关键点

6.1需求分析的关键点主要包括以下几个方面:

  1. 明确用户需求与产品需求的区别:这是需求分析的基础,需要区分用户需求和产品需求,确保产品或服务真正满足目标用户的需求。

  2. 将用户需求转化为产品需求的方法:通过深入细致的调研和分析,将用户非形式的需求表述转化为完整的需求定义,确定系统必须做什么。

  3. 深入挖掘用户动机:在需求分析中,了解和分析用户的动机是非常重要的,这有助于更好地理解和满足用户的需求。

  4. 筛选和优化需求:产品经理需要筛选和优化接收的需求,确保需求的质量和优先级,以提高产品质量和用户满意度。

  5. 收集需求、整理需求、分析需求、确认需求和编写需求文档:这是需求分析的一般流程,包括收集、分类、筛选需求、分析需求等步骤[[3]]。

  6. 使用合适的需求分析方法和工具:根据不同的项目需求和使用场景,选择合适的需求分析方法和工具,如HWM分析法、功能分解方法等。

  7. 考虑需求的业务诉求、目标用户的用户诉求、分析总结需求目标:合理地归类接收的需求,明确需求的业务诉求,明确目标用户的用户诉求,分析总结需求目标,并给设计提供依据。

  8. 需求评估分析方法:包括模糊聚类分析、质量功能展开、KANO模型分析、A/B测试等,这些方法可以帮助评估需求的质量和可行性[[22]]。

综上所述,需求分析的关键点是多方面的,涉及到从明确用户需求到优化需求的整个过程,以及在此过程中采用合适的方法和技术来确保需求的准确性和有效性。

6.2需求分析中的HWM分析法具体是什么,如何应用?

HWM分析法,即"How Might We"(我们可以怎样),是一种用于需求分析和问题解决的方法。它的全称为"How Might We",即"我们可以怎样"。在这个过程中,我们假设问题是可以解决的,只是我们尚不知道如何解决。这种方法强调的是通过头脑风暴的方式,最大范围地搜集产品的各种可能性,然后抽象地整理出这些想法背后所隐藏的核心概念和产品需求,快速梳理出正确的产品设计方向。

应用HWM分析法时,可以分为五个步骤:首先是明确用户场景问题,其次是HMW分解问题,然后是扩展思路,接着是使用不同的分解思路如积极、转移、否定、拆解、脑洞等来拆解许多不同的解决方案,最后是抽象地总结这些想法并确定解决方案。这一过程中,工具的使用也很重要,例如思维导图可以帮助清晰地展示问题和可能的解决方案。

此外,HWM分析法不仅仅局限于产品需求分析,它还涉及到对人类行为和社会系统的分析,以识别存在的问题和潜在的风险,并制定出相应的应对策略和措施。这表明HWM分析法具有较强的综合性和灵活性,能够适应不同领域的需求分析。

HWM分析法是一种通过广泛探索和思考各种可能性来解决复杂问题的方法论,它要求团队成员共同参与,通过明确问题、分解问题、扩展思路、采用多种分解思路以及最终的抽象总结,来寻找最合适的解决方案。

7.需求收集技巧

7.1 需求收集技巧有哪些,特别是在多渠道反馈收集方面的策略?

需求收集技巧在多渠道反馈收集方面的策略主要包括以下几点:

  1. 多渠道反馈收集:企业可以提供多种反馈渠道来确保用户能通过多种方式进行反馈。这包括但不限于在线调查问卷、社交媒体平台、用户论坛等,以确保能够覆盖到不同的用户群体和使用场景。

  2. 观察法:通过观察目标用户的日常行为来理解他们的真正需求。这种方法可以是主动的,即观察用户的行为和工作流程,也可以是被动的,如收集用户对设计原型的反馈。这种方法有助于深入了解用户的实际操作习惯和需求,从而提供更准确的产品改进建议。

  3. 访谈和问卷调查:通过与利益相关者进行沟通和访谈,了解他们对于产品或服务的需求和预期。同时,设计有效的问卷调查也是需求收集的重要手段,可以帮助收集更广泛的需求信息。

  4. 文档分析:利用文档(如用户手册、操作指南等)进行分析,可以发现那些不易直接表达但对产品改进至关重要的需求。这种方法适用于那些需要详细说明或解释的产品功能。

  5. 用户反馈渠道:除了上述提到的多种渠道外,还应考虑建立专门的用户反馈机制,如定期发布用户调查问卷、开放日活动等,以直接从用户那里获取反馈。这些反馈可以帮助团队及时了解当前产品或服务的不足之处,以及潜在的用户痛点。

多渠道反馈收集策略要求企业综合运用多种技术和方法,既要注重面对面的沟通和观察,也要充分利用网络和数字工具,同时不忘通过文档分析等方式深入挖掘用户需求。这样的策略能够帮助企业构建更加全面和准确的需求收集系统,为产品和服务改进提供坚实的基础。

7.2 如何有效地进行用户访谈以收集需求?

有效地进行用户访谈以收集需求,首先需要确保访谈环境轻松愉快,避免给受访人带来社会压力。用户访谈是一种有计划、有目的、有意识的过程,通常有明确的时间安排和谈话主题。在准备阶段,应具备正确的预备知识,具备细致的洞察力、耐心和责任感。

在访谈过程中,应积极倾听受访者的意见,不要害怕沉默,也不要强制用户回答。可以在用户回答后以自己理解的方式重复答案,以避免对用户的回答产生误解。此外,正确并恰当地提出问题是解决困惑的第一步,用户访谈首先是一门艺术——说话和倾听艺术,也是提问的艺术。

有效的访谈需要满足提对问题、正确沟通、提炼转化三个条件。这意味着在访谈中,不仅要提出正确的问题,还要通过访谈技巧有效获取用户信息,并将调研信息转化为洞察分析。

观察法也是理解用户真正需求的有效方式之一。通过观察用户的日常行为,可以主动或被动进行访谈,以理解他们当前的工作流程。这种方法有助于深入了解用户的需求和偏好。

总之,有效地进行用户访谈收集需求的过程包括创造友好的访谈环境、准备充分的预备知识、积极倾听和正确提问。同时,结合观察法等其他方法,可以更全面地理解和满足用户需求。

8.需求分析的误区

避免需求分析常见误区的具体步骤和方法:

  1. 目标驱动,结构分解:首先,明确需求分析的目标是非常重要的。这包括了解项目旨在达成的目标,如吸引新用户、保留老用户、提高用户活跃度或产生营收等。接着,根据这些目标,结构分解出为了达成这些目标而需要的需求。

  2. 避免把用户描述当作需求:在需求分析中,不应该仅仅基于用户的描述来确定需求。这种做法很容易导致需求偏离实际业务目标,从而无法满足核心业务的要求。

  3. 避免把数据表象当需求:需求分析时,不应只关注数据表现,而忽视是否有偏离业务的情况。过分依赖数据可能会误导需求分析,导致开发出来的产品与预期目标不符。

  4. 避免把竞品功能当需求:在需求分析过程中,不应该简单地将竞品的功能照搬过来。每个产品的市场定位和目标用户群体都有所不同,直接复制竞品的需求可能会导致产品失败。

  5. 关注用户及业务目标并重:在进行需求分析时,不仅要关注用户需求,还要关注业务目标。确保需求分析能够支持业务目标的实现,而不是单纯地迎合用户需求。

  6. 使用严谨而科学的分析方法:需求分析不应该是一种随意的思考过程,而是需要遵循一定的科学方法和步骤。例如,可以使用马洛斯需求模型来分析需求,然后分析用户和场景,最后分析用户期望。

  7. 识别伪需求:通过学习和实践,学会辨别哪些是需求分析中的常见伪需求。这包括识别那些看似合理但实际上并不符合业务逻辑或目标的需求。

需求分析的误区包括没有进行有效的需求管理、对需求理解不够深入、忽视了需求的可追踪性和变更控制机制等。为了避免误区,产品经理应该采用敏捷开发方法,建立严格的需求变更管理流程,对任何需求变更进行详细讨论、评估、记录。此外,正确分辨用户提出的是需求还是解决需求的方案也是避免的一个误区。

综上所述,产品经理在进行需求分析时,需要从宏观到微观全面考虑,利用多种工具和方法进行深入分析,同时注意需求管理的各个方面,以确保产品能够满足市场和用户的真实需求,与公司的战略目标和愿景保持一致。


作者:西边一山
来源:mdnice.com/writing/b3ea0873bba04ab98767930c4d9a268b
收起阅读 »

2023总结:30岁,结束8年北漂回老家,降薪2/3,我把人生过的稀烂

一转眼又快过年了,回想整个23年,简直是我人生中最黑暗的一年(之一)。 23年,我30岁,在北京干了8年程序员。30岁这年我做了一个决定:结束8年北漂生涯,回老家(一个三线城市)自己创业,去做自媒体。 一、为何做出这个决定 这个决定也不是一时拍脑袋做出的决定...
继续阅读 »

一转眼又快过年了,回想整个23年,简直是我人生中最黑暗的一年(之一)。



23年,我30岁,在北京干了8年程序员。30岁这年我做了一个决定:结束8年北漂生涯,回老家(一个三线城市)自己创业,去做自媒体。


一、为何做出这个决定


这个决定也不是一时拍脑袋做出的决定,导火索是在22年:


那时候大环境不好,大家都越来越卷,下班的时间也越来越晚。


放假回家亲戚朋友总说,你在北京996这么累,图啥啊,工资是高点,但是完全没有生活啊。而且你在北京漂到啥时候是个头?你又买不起房,又没户口,早晚得回来吧。


我仔细想想也有道理,活了这么多年了都在当牛做马,被pua,还得面临35岁危机,真的受够这种生活了!所以那时候心里埋下了一颗种子:我要去浪浪山的那边看看!


其实我本身就是一个喜欢自由的人,这么多年那句“打工是不可能打工的,这辈子都不会打工”一直激励着我,我想自己有一天也能实现不打工这个目标。


于是22年底我做了一个决定:23年去山的那边看看大海的样子!拿完年终奖就辞职!去创业,去开启我的新的人生!


在准备辞职前的几件事情,都让我更加坚定了辞职的决心:



  1. 那时候还没有放开,在家线上办公,本来在公司办公是995,晚上9-10点下班了基本就没啥事情了,但是在家就不一样了,每天各种电话、视频会议,甚至十一二点都要开会,恨不得让你24h都在线,生活和工作基本都没有边界。那个时候只要听到会议呼叫的声音,内心就一紧,心中默默祈祷不要出什么幺蛾子,都快成心理阴影了。

  2. 当时得了新冠也只敢请了一天假,第二天晕晕乎乎的就继续开始工作了。因为我知道,落下的工作最后还得你自己加班完成,否则领导最后还会赖你延期。

  3. 周末也需要随时在线,需要及时回复群里的消息,需要随时解决线上的问题,否则就会打上工作态度不好的标签,绩效肯定低。导致我周末基本不敢出去,出去也得随时看着手机,看有没有@你的消息,整天提心吊胆,玩也玩不好,还不如在家躺着。


我觉得这不是我想要的生活,每天太累了,身体累不算,心还累,生怕自己负责的业务出了什么问题,如坐针毡,如芒刺背,如履薄冰。


二、我辞职了


终于,熬到23年,拿到年终奖后,我决定提出离职。


当时身边有些人劝我不要辞职,说现在环境不好,更不应该放弃你的老本行,去做啥自媒体。


我当时内心嗤之以鼻,心想程序员这行也就干到35岁,而且现在卷的不行,加班加的身体都快废了,这行岁数大了没前途!我趁现在30岁还年轻,创业正值当年,辞职改行的选择非常有战略眼光!(当时真的是感觉杰克马附体,准备在这个三十而立的年纪,大干一场!)


2b5f9de5dbc7cd40403819a50d693574.jpeg


当然我也不是脑袋一热就想着辞职去做自媒体,辞职前我做了充足的准备,和很长时间的调研&分析:



  • 我作为一个互联网人,做实体店肯定不是我擅长的,肯定只能从互联网上选择行业,互联网项目有很多:个人工具站,知乎好物,闲鱼二手书,小红书带货,抖音带货,抖音个人ip,公众号写作,短剧cps,小说推文,知识付费等等的项目,我可以说都看了一个遍,其中抖音现在流量最大,要做风口上的猪,做抖音相关肯定要容易很多。

  • 然后我也学习了一些创业相关的知识,比如如何找对标,如何分析对方商业模式,参加了很多知识付费的圈子,然后还报了小红书和抖音的培训班,总共加起来得有1w多呢。

  • 而且我还预留了充足的资金,我做了最坏的打算,就算我一分钱不挣,也够我活3年呢,我不会3年都创业不成功吧!(此处白岩松表情包:不会吧!.jpg)


u=1021210702,2199782272&fm=253&fmt=auto&app=120&f=JPEG.webp


三、想象很美好


为了这次创业,我还制定了计划,年度计划,季度计划,月计划,周计划,天计划,真的非常详细。


我也要很自律,每天按时起床,锻炼,学习,做业务。这次我真的抱着必胜的决心来做!


当然我也提前列出可能要遇到的风险,并思考解决方案:


比如项目进展慢怎么办,拖延症怎么办,家人反对怎么办,朋友约吃饭打乱我的计划怎么办,遇到困难我该怎么应对等等


这么一套组合拳下来,我觉得已经万事俱备,只差开干了!


四、现实很残酷


4月我如期辞职,当时正值清明节,淅淅沥沥的小雨并没有浇灭我开启新生活的热情。辞职后,我就按计划开始早睡早起,锻炼,学习,搞创业的事情。


但是马上就被打脸了,这是我创业中遇到的第一个难题,也是我万万没有预料到的


就在我创业后的不久,我患上焦虑症,失眠了,而且还很严重,就是那种从晚上11点躺下,躺到早上6点才睡着的那种失眠,而且还时不时的心悸。


我万万没想到会患上失眠症。因为我觉得没有上班的压力了,想啥时候干活就啥时候干活,想干多少干多少,想啥时候下班就啥时候下班,也没人pua我了,还有时间锻炼,应该睡得更好才是。


但实际并不是这样,对于一个从小被学校管,长大了被公司管的芸芸众生来说,创业实际是这样的:



  1. 你会非常忙,比上班还要忙,因为你之前是螺丝钉,做好自己的本职工作就好了,现在事无巨细,都你一个人。比如做自媒体,从开始的账号定位-》内容选题-》写脚本-》置景&拍摄-》后期剪辑-》选品-》商务对接-》客服-》用户社群运营,所有的环节,都得你自己一个人。然后视频没流量怎么办,违规了怎么办,付费转化率低怎么办,还是只有你自己去解决。(之前公司让你干啥你干啥,你只需要规定时间完成你的任务就好了)

  2. 面对大量的自由时间,你根本不会支配时间,因为很多环节你都是小白,要学习的东西太多,但是你天天光学习了,每天看似很忙,但是看不到产出,导致你就很沮丧。(之前你只做熟悉的工作,产出是有保证的)

  3. 行动困扰,没有目标感,没有人给你一个目标&方向,你不知道你现在做的事情对挣钱有没有价值,你会迷茫,你会时常自我怀疑。(之前你只是专注领导安排的任务,至于这个任务能不能帮公司挣到钱,那是公司的事情,你关心到手的工资而已)

  4. 没有成就感,认同感。因为现在你很多事情要从0开始,比如写文案要求写作能力,拍视频要求表现力,搞流量要求你有运营&营销的能力 ,相比之前做熟悉工作,感觉上会有落差(之前工作中都是做你擅长的领域,每完成一项任务也很有成就感,做的出色还能收获同事和领导的认可)

  5. 和社会断了链接,没有存在感,归属感(这是人类的基本需求之一),你不属于任何一个群体,没有人赞扬,尊重,接纳你,甚至你想被骂两句也没人鸟你(之前在公司,做的好了领导或者同事会夸你两句,做的不好了可能会给你建议,起码有人能倾诉,能交流,能寻求帮助)

  6. 没有了收入,眼见钱包一天天变少,你肯定会焦虑。但是更让你焦虑的,是你不知道未来什么时候能挣到钱。更更让你焦虑的,是不知道最后能不能挣到钱。(之前工作压力不管有多大,多累,起码你还有工资,你还有吃饭的钱,这是底气)


所以在此奉劝有裸辞创业想法的人,千万不要裸辞!裸辞创业九死一生! 正确的做法是一边工作愿一边做副业,等副业的收入和工资差不多甚至超过工资了,再去辞职。有人会说,我工作那么忙,根本没时间搞副业啊。我之前也是这么想的,但是现在我会告诉你:没有时间就去挤出时间,每天晚睡或者早起一会,周末也抽出时间搞。这点问题都解决不了?创业的遇到问题会比这难十倍!如果这个你觉得太难了,那我劝你还是老老实实打工吧。


但是我已经裸辞了,没办法,只能去解决问题,我开始吃助眠药,喝中药,有些好转,但也没治好,只是比之前好点。


就这么拖着残血的半条命,我坚持了半年多,一半时间学习,一半时间实践,搞了两个自媒体号,第一个号违规被封了,第二个号流量也没啥起色。这条路是越走越看不到希望,每天晚上都不想睡觉,因为害怕明天的到来,因为明早一起床,眼前又是一片黑暗。


五、彻底崩溃


11月,因为种种原因和媳妇生了一场气,我觉得对于我创业,她不鼓励也就算了,在我状态这么差的情况下还不能对我包容一点,甚至有点拆后台的感觉,那几天我就像一个泄了气的皮球,内心被彻底击垮了。(所以现在有点理解每个成功男人的背后,都有一个伟大的女人这句话的含义了)


终于,在创业的压力,8个月没有收入的恐慌,焦虑失眠心悸的折磨中,我决定放弃了。


失败了,彻彻底底的失败。回想这次经历,就好像之前在一艘航行的货轮上打工,然后受不船上的种种压榨,终于鼓起勇气,自己带着一艘救生艇,跳海奔向自己想要的自由。结果高估了自己的目前的实力,经不起茫茫大海狂风骤雨,翻船了。。濒临溺亡。。。


六、重新找工作


放弃后的那几周,我开始熬夜,开始暴饮暴食,之前的运动也放弃了。整天在家里拉着窗帘,除了吃饭就是躺在床上刷手机,让我尽可能分散注意力,减少内心的痛苦。


但是这样的状态也不是事儿啊,目前肯定是不想再去面对创业的事情了,那只能去找个工作先干着了。


刚开始找工作内心又有不甘,因为一个三线城市比起北京来说,不管是工作机会,环境,薪资来说,都差太多。


但是没办法,我现在的感觉就是快溺死了,我现在急需一个救命稻草,活下来,是我目前的首要任务。


于是在网上海投了一遍,结果惨不忍睹,根本没几家公司招人,前前后后一个月,真正靠谱的面试就一家,是的,只有一家。


好在这家也顺利拿了offer,是一家刚创业的公司,一共十几个人,薪资只有原来1/3多点,但是拿到offer那一刻我依然有些激动,我感觉我活下来了,不管怎样,现在能喘口气了。


七、迷茫的未来


现在上班已经一个多月了,公司挺好,不加班,基本上7点前就都走了,离家也挺近,骑个共享单车也就10分钟。这一个月,焦虑没了,不心悸了,失眠也好了。每天就是按部就班上下班,完成老板给的任务,其他的事情也不用自己操心,终于又做起自己熟悉且擅长的事情。


但是内心还是有落差,本来北京好好的工作自己作死给辞了,要不这一年也能攒不少钱呢,现在不但钱没了,这几个月还花了好几w,最后还差点嘎了。


其实入职这家公司前,北京之前的同事问我要不要回去,说现在正忙,我说你先问问吧。


我当时也纠结,如果真的能回去,我还要不要回去,毕竟在那边挣一个月顶这边仨月。但是回都回来了,再去北京可能就一辈子留北京了吧。


不过后来同事说年前没有招人计划了,可能要年后了,如果招人到时再联系我。正好我不用纠结了,这可能就是命运的安排吧。


不过真的想问问你们,如果到时有机会,是继续北漂呢,还是选择在老家呢?


八、结语


说实话,我现在知道了,山的那边还是山,我不知道什么时候才能看到海,甚至我可能一辈子都看不到海了。不过目前想的就是,调整好状态,先走一步算一步吧。


30岁的年纪,学会和自己和解,学会接受自己的平庸,但是依然要努力,毕竟在这个阴雨连天的环境下,没有伞的孩子只能努力奔跑。


作者:骆驼箱子
来源:juejin.cn/post/7330439494666453018
收起阅读 »

7年Android仔的逆袭人生

1.引言 最近在代码人生模块,看到了很多优秀的同行分享自己的人生经历。有感情的,有创业的,有独立开发者的。看完后感慨良多。为此我也想讲讲我的成长经历。相信能给各位一定的启发。 2.毕业 我是一个来自湖北农村的少年。从小到大学费都是父母卖粮食,卖棉花,找亲朋好友...
继续阅读 »

1.引言


最近在代码人生模块,看到了很多优秀的同行分享自己的人生经历。有感情的,有创业的,有独立开发者的。看完后感慨良多。为此我也想讲讲我的成长经历。相信能给各位一定的启发。


2.毕业


我是一个来自湖北农村的少年。从小到大学费都是父母卖粮食,卖棉花,找亲朋好友,东拼西凑的。要不是勉强考上二本大学。可能现在的我就在工厂搬砖。我记得大四快出去实习的时候,家里没有钱给我路费,硬是卖掉家里十几袋麦子,给我凑的。同期的同学别人家里都是给5000.6000的。而我只有2500。就这样我带着仅有的2500,拉着一个破旧的行李箱踏上南下之旅。怀揣着兴奋,对未来美好的期待来到深圳。运气比较好,很顺利的找到一家公司。那家公司给我开了10000/月的工资。你们知道吗。我是多么多么的兴奋啊。1万啊!,我从来没有掌管过这么多钱。甚至我家里从来没有过1w。过去的二十多年,我的物质生活一直没有被满足过。吃的,用的,都是差人一等。第一台华为手机,也是硬生生用了4年。哪一年我22岁。现在想起来,依旧很兴奋。当时把工作的事情,告诉了父母。父母开心的不得了。我爸在家对我妈说:“我就知道儿子,会有出息”。


3.动荡


本来一切都在向好的方向发展,可是老天爷却给你开了一个玩笑。2017年7月份的一天,一通电话彻底打乱了我的生活节奏。就像一块砖头一下子丢进水里,“咚”的一声。砸在我的心里。电话那头,我姐姐哭着叫我回去,叫我赶紧回去。她告诉我:“爸爸去世了,你赶紧回来,赶紧回来”。面对突如其来的恶耗。经历过的人,应该都知道。那一刻大脑实际上是懵的。呼吸紧促,仿佛喘不过气。内心会质疑这个消息的准确性。觉得不可能,不可能。在家里好好的,好好的,为什么会突然间走了。时至今日,即使过去多年,回想到这些。我依旧会泪流满面。哪一年我22岁。本该幸福的家庭,却发生这样的变故。父亲是一个家庭的基石。是子女坚实的靠山。哪一年,我失去了依靠。也失去了一个完整的家庭。
往后的这些年,我时常梦见我父亲。梦见他还活着,梦到他再和我说话。


父亲是因为急性心肌梗塞走的。发生心肌梗塞的时候,实际上身体会有反应的,例如 四肢无力,例如心跳加速。在出事的前几天,他因为身体不舒服,去过诊所问诊,但是因为医疗条件的不足,加上之前整个家族没有这样的例子。所以没有检测出来。这件事让我意识到世上很多事,我们无能为力,唯有学会的接受


同时,我也会不断的追问自己,为什么会出现在我的身上。因果因果,有这个果,必然有这个因。这个因在哪里呢。我想是这几个因:1.农村人的健康意识差 2.身体不舒服 总觉得自己扛扛就过去了 3.本身存在各种疾病,例如高血压。4.农村的医疗条件差


同样世上很多事,也可以用因果来解释。例如溺水身亡,触电,交通事故。一桩桩悲惨的事件的后面,肯定是有很多因。触电之前,可能有过多次,湿手触碰电器的行为,进而养成习惯; 交通事故之前,可能经常抢红绿灯,经常超车。


也正是因为这个意识的养成。帮助了我改变人生,当然这都是后话。在我父亲去世的三个月之后,爷爷因为接受不了打击,也去世了。仿佛是潘多拉魔盒被打开了,让这个家族饱受磨难。


4.工作


处理完家里的事之后。又匆匆返回深圳,继续当螺丝钉。整个人思想压力也变重了。我未来结婚,买车,买房,给母亲养老都得靠自己。每当我望向身后,我看到的是深渊。我不敢松懈,我不敢像一个正常人那样生活,因为我没有依靠,我只有自己,我得努力,拼搏,奋斗。周六周天会抽出一天的时间去图书馆学习。现在想想,自己能坚持下来,也挺佩服曾经的自己。或许是上天的眷顾,也或许是运气好。在面试OPPO的时候。面试官的问题,正好是我前两天写的博客。于是顺理成章的进入了大厂。在OPPO呆了2年多,技术上得到很大的提升,经历过裁员,经历过背锅,经历过职场的勾心斗角。这段工作经历,拔高了我的世界观,让我从懵懂的少年,蜕变成一个合格的职场人。同时这段经历也间接的改变了我的人生轨迹。


5.感情


自从家里发生变故后,我对未来的规划更加清楚。不管是工作,还是感情上的事。都会提前做准备。例如在oppo的时候。注意到当时一个表现优异,绩效A的同事,来年却转岗了。通过他,我知道了部门发展不顺利,未来可能有裁员的风险。于是就开始私下准备面试的工作。21年一整年,我私下面试了接近40家公司。22年又面试了10多家。当时就明显感受到市场的寒冷。意识到22年假如不跳槽。可能就要一直待在OPPO,等待被裁。于是就果断的跳槽到顺丰。拿到了将近40%的涨幅。虽然后面又离开了顺丰。但是现在来看,当初的选择是没有错误的。


在我年仅26岁的时候。我就在考虑结婚的事,因为我笃信 一个好的伴侣抵得上百万资产,抵得上几十万的高薪工作,她直接决定了你下半生的生活质量。同时我也知道自己一无所有,无存款,无家庭,甚至攒下的钱都不够房子的首付。但是我审视了自己一番。发现自己还是有一些优点的,例如 五官不差,身高1.8,工作也还行,年薪30多万。了解了自己的优点和缺点之后。就开始着手改变自己。


例如跑步减肥从180减到150,每天5公里户外跑步。同时也积极参加一些穿衣打扮课程。了解自己的穿衣风格。 有时间就去相亲会相亲。
说到相亲,我可是相亲界老手了。😁😝 前前后后相亲了 20多场。最后找到了现如今的老婆。


在这段经历当中,一个意识深深的插入到了我的脑海中。那就是 任何事都是有俩面性的,看待事情,争取看到事情的俩面性。这样自己才能提前做准备。


例如:程序员以高薪著称,但是反面就是,肥胖,脱发,油腻。这在相亲市场上是非常不利的。


工程型人才,往往看不上溜须拍马,耍嘴皮子那套。但是随着自媒体的盛行,发现自媒体做的好的人,恰恰都是耍嘴皮子,能放下身段,脱下长衫的人。这个认识正对应了一句话:”当你凝视深渊的时候,深渊正在凝视着你"


6.后记


写这篇分享的时候,老婆已经怀孕8个月了,再有2个月,我就要当爸了。孩子的名字都已经想好。目前定居于深圳,因为老婆家庭条件好,老丈人给了一套豪宅居住。让我免于房贷的压力。有充足的精力为下一个10年奋斗。说到这里我很感谢老婆一家人。他们没有嫌弃我穷,反而时时刻刻照顾我的自尊心。他们一家是我的人生贵人。我问了老丈人很多问题。他都能给我带来不一样的视角,耐心讲给我听。这是多少钱都买不来的。以后有机会可以在聊聊他的一些观点。有一些深深的刻在我的脑海中了。


作者:薯条1492738192844
来源:juejin.cn/post/7351658802393546802
收起阅读 »

反转反转再反转,揭秘人心深处的“恶意”

“……真是过分,我每天可是难过得要死。有个爱管闲事的邻居,每天都来找我,我没办法,只好去上学,都快给他烦死了。” “老师和学生的关系建立在一种错觉上。老师错以为自己可以教学生什么,而学生错以为能从老师那里学到什么。重要的是,维持这种错觉对双方而言都是件幸福的...
继续阅读 »

“……真是过分,我每天可是难过得要死。有个爱管闲事的邻居,每天都来找我,我没办法,只好去上学,都快给他烦死了。”


“老师和学生的关系建立在一种错觉上。老师错以为自己可以教学生什么,而学生错以为能从老师那里学到什么。重要的是,维持这种错觉对双方而言都是件幸福的事。因为若看清了真相,反而一点好处都没有。我们在做的事,不过是教育的扮家家酒而已。”


是什么样的经历让他说出这样的话呢?我不明白。


大家好,我是杰哥


昨天晚上凌晨三点,我终于第三次翻完了《恶意》。这本书,真的让我欲罢不能!每次阅读都像是一次心灵的冒险,让我惊叹不已。


作者东野圭吾巧妙地运用手记的方式,将故事的发展娓娓道来。那些看似简单平实的文字,却隐藏着令人震撼的真相。他对复杂人性抽丝剥茧的深刻描画,简直让我眼花缭乱,哑口无言。


故事围绕着一起谋杀案展开:畅销书作家在出国的前一晚于家中被杀,凶手很快便落网了。但别以为这只是个简单的“谁是凶手”的故事,其实更多的是”我为什么要杀他“的故事。


凶手对作案动机语焉不详,倒是引起了著名侦探”加贺“的兴趣,他凭借自己一贯对于人性觉察比较敏锐的”直觉“,以及自己曾经作为老师所亲身经历过的“校园暴力”事件,对”作案动机“展开了缜密的分析与调查。经过层层曲折的调查,终于将真实的动机呈现在我们的面前(此处故意不剧透,以免影响了大家的阅读体验)。我只能说,得知真相的你,一定会被震撼到,从而陷入深思。


我是一个悬疑推理类书籍的书迷,看过很多悬疑推理类的书籍,而这本则是一本题材与故事都很新颖且富有创造力,结局也会很让人意外的其中之一。


读这本书的过程中,我就像是坐过山车一样,情绪起伏不定。每当我以为抓到了真相的尾巴,作者就会巧妙地用一个新的情节把我甩回去。反转再反转,直到最后,我才恍然大悟:哦,原来真相是这样的!大概真正优秀的悬疑推理类小说的作家的仅有的几部作品中,才可以与读者的互动达到这样的效果吧。


这本书不仅仅是悬疑,它更深刻地探讨了人性。恶意,这个看似抽象的概念,在书中被具象化,变得触手可及。它让我不禁深思,人心的黑暗面到底能有多深,我们又该如何面对和控制自己内心的恶意。


东野圭吾的笔下,每个人物都有自己的秘密,每个线索都可能是个陷阱。他的作品,让人读起来往往感觉惊险又刺激,恨不得一口气读完,甚至连旁边的手机也被冷落了。


总之,如果你喜欢心理悬疑,喜欢深度剖析人性的作品,那《恶意》绝对不容错过。它会让你在紧张刺激的阅读中,体验到心灵的震撼!


作者:舒米勒
来源:mdnice.com/writing/924e74e14de748d3b72493d7224aba0d
收起阅读 »

跳舞的人

跳舞的人 从我们大学的老校区南院门口进入,迎面便能看到庄严的主楼。 河北大学主楼 主楼后面是一段有花草树木的路,旁边是多功能馆。在主楼和多功能馆中间,有一块空旷的场地,人们清晨、傍晚常常在那里嬉戏玩耍。 大学一年级下半年、...
继续阅读 »

跳舞的人


从我们大学的老校区南院门口进入,迎面便能看到庄严的主楼。



河北大学主楼

河北大学主楼


主楼后面是一段有花草树木的路,旁边是多功能馆。在主楼和多功能馆中间,有一块空旷的场地,人们清晨、傍晚常常在那里嬉戏玩耍。


大学一年级下半年、大学二年纪一整学年我都是在主楼内的我们学院的机房里值班的。所谓值班就是,我晚上需要在机房对面的小屋里睡觉,白天需要管理好机房的日常使用工作。


因为早晨经常需要帮在机房上课的老师学生开门,所以在主楼住的时候,我会醒的比较早。


醒来后,我会先去食堂吃饭,然后在主楼后面散散步,转一圈。


有天在散步的过程中,听到了主楼前的方向有音乐的声音,我对这音乐比较好奇,便循着声音来到了主楼和多功能馆旁的空旷场地。这里放着一个看起来又大又重的音响,音乐便是从这个音箱里传出来的。在大音箱旁边,一个男生在跟随着音乐跳着舞。


早晨的时间是比较充分的,我便在这站了一会,发现跳舞的男生,每个舞蹈都会重复很多遍。我并不懂跳舞,只是能够感觉出来每一遍舞蹈,都是那么认真、那么投入,我猜他很热爱跳舞吧。


后面每每有时间,我都会走到那块空旷的地方,也经常能够看到他在这里跳舞。我想,这块空旷的场地就是他的舞台吧。


有天早晨,雨下得很大,我很早便被雨声吵醒了,我突然想看看「那个跳舞的人,下雨天会不会来练习跳舞呢?」


我便穿好衣服、鞋子,来到主楼不会被雨淋到的台子上。不一会,我便看到一个打着大伞的男生,拉着音箱走了过来。随着男生越来越近,我看清了,就是他——那个跳舞的人


他把音箱拉离地面,一步一步地走上台阶。我心里想,这么大的音箱,拉到台子上,不重吗?


他慢慢近了,来到了我旁边,我和他互相说了声你好,他便打开了音箱,放起了音乐,跳起了舞来,依旧那么认真、那么投入。


外面很冷,看到他来了,心里的疑问算是解开了,我便向主楼里面走去,回到了机房。


在回机房的路上,我便想,因为热爱,音箱便不会重了吧。


作者:随机的未知
来源:mdnice.com/writing/6882be2b53a04567a77d7be826eef49c
收起阅读 »

Redis不再 “开源”

Redis 官方今日宣布修改开源协议 —— 未来所有版本都将使用 “源代码可用” 的许可证 (source-available licenses)。具体来说,Redis 将不再遵循 BSD 3-Clause 开源协议进行分发。从 Redis 7.4 版本开始,...
继续阅读 »

Redis 官方今日宣布修改开源协议 —— 未来所有版本都将使用 “源代码可用” 的许可证 (source-available licenses)。


具体来说,Redis 将不再遵循 BSD 3-Clause 开源协议进行分发。从 Redis 7.4 版本开始,Redis 采用 SSPLv1 和 RSALv2 双重许可证。Redis 源代码将通过 Redis 社区版免费提供给开发者、客户和合作伙伴。

SSPL:Server Side Public License

RSAL:Redis Source Available License Redis 产品家族的具体许可证如下:


根据新许可证的条款,托管 Redis 产品的云服务提供商将不再允许免费使用 Redis 的源代码。例如,云服务提供商只有在与 Redis(Redis 代码的维护者)达成许可条款后,才能向用户交付 Redis 7.4。

Redis 官方表示:

实际上,Redis 开发者社区不会发生任何变化,他们将继续拥有双重许可证下的宽松许可。同时,Redis 负责的所有 Redis 客户端库将保持采用开源许可证。 Redis 将继续支持其庞大的合作伙伴生态系统(包括托管服务提供商和系统集成商),并独家访问 Redis 通过其合作伙伴计划开发和提供的所有未来版本、更新和功能。 现有 Redis Enterprise 客户没有变化。 总的来说,对于使用 Redis 开源版本和新版本的 Redis 的最终用户(使用双重许可证进行内部或个人使用),没有任何变化。

对于使用 Redis 构建客户端库或其他集成的集成合作伙伴,同样没有任何变化。 Redis 对这次修改开源协议的举措十分坦诚,他们承认 Redis 不再是 OSI 定义下的“开源”项目。但他们仍是开源理念的支持者,并会继续维护开源项目。


原文:https://mp.weixin.qq.com/s/9_-w6lF7ffiu49WbEORPtQ

收起阅读 »

我不敢把水烧的太开

我不敢把水烧开,那样家里会有两个沸物。我也不敢把房间打扫的很干净,我怕太干净,垃圾只剩下我。我常坐在窗口看着窗外发呆,这悲伤来的没有油头。床上有两个枕头,一个是我的,另一个也是我的,因为我裂开了。我也经常熬夜,因为天冷了,时间就不说了。白天面对的是生活,夜晚面...
继续阅读 »

我不敢把水烧开,那样家里会有两个沸物。我也不敢把房间打扫的很干净,我怕太干净,垃圾只剩下我。我常坐在窗口看着窗外发呆,这悲伤来的没有油头。床上有两个枕头,一个是我的,另一个也是我的,因为我裂开了。我也经常熬夜,因为天冷了,时间就不说了。白天面对的是生活,夜晚面对的是灵魂,一半的时间来生存,剩下的时间拿来滋养灵魂!我熬的不是夜,是我短暂的自由。青春献给了梦想,梦想败给了现实。小时候无忧无虑,倒头就睡,长大后忙于生计,失眠怎么常态。背井离乡的颠沛流离,不过是为了碎银几两。习惯了一个人的独处,也慢慢接受了自己的平庸。我们不是故事里的主角,也没有主角光环!我们只是茫茫人海中的渺小一个。不曾坐过飞机,也没喝过星巴克,更没有用过奢侈品。小时候的自由人,长大后的笼中鸟。以前叫醒你的是父母,现在叫醒你的是生活。我们变得好像是机器人,每天起床的意义就是重复的工作。 我似乎感受到那袭来的风划过,渴望度图欣赏,但更吹醒了我的意识,要继续生存下去,夜深人静是自由醒来清晨是生活,朋友人间自由身,却非人间自由人,看似自由自在,实则身不由己。


我不敢轻易点燃热情,以免世界再添两个燃烧的灵魂。我也不敢让心扉过于透彻明亮,只怕纯净得只剩下自我孤独。我常常倚在窗前凝望星空,那份寂寥悄无声息地蔓延。床榻上有两个梦乡,一个属于清醒时的我,另一个属于深夜里破碎的我。我时常与黑夜为伴,仿佛只有此刻,才握住了片刻的宁静。白昼应对的是繁杂尘世,夜晚则是对内心世界的对话,一半的生命为了生存而奋斗,另一半则用来沉淀和丰盈心灵。我熬的不只是夜,更是那一份难能可贵的自我空间。青春曾向理想倾注所有,而理想最终却在现实中折戟沉沙。儿时懵懂无知,酣然入梦,成人后疲于奔命,反倒是失眠成了常态。远离故土、四海为家,无非是为了那些散落各处的铜板。渐渐习惯独自行走,也逐渐接纳了自己的平凡无奇。我们并非小说里的主人公,身上也没有主角光环庇佑,我们只是芸芸众生中的一员。未曾体验云端飞翔,亦未尝品鉴星巴克的香醇,更谈不上拥有奢侈品牌的光环。曾经那个随性率真的孩子,如今已变成囚禁在生活牢笼中的飞鸟。过去的黎明由父母唤醒,现在的黎明却是生活的催促。我们如同被设定程序的机器,日复一日只是为了重复的工作奔波。


我恍若感受到那阵疾风吹过,虽有心去追逐欣赏,但它更像是一记警钟,提醒我要坚韧地活下去,深夜的清醒是对自由的领悟,破晓的苏醒则是对生活的担当,身边的朋友皆似世间自由行者,却非人人能真正活得洒脱。表面看似悠然自得,实则都身陷无形的生活枷锁之中。


作者:Young_
来源:mdnice.com/writing/ac9b73a2a7f84f1eb843a6c404a82701
收起阅读 »

《健听女孩》——一部感人的电影

故事 《健听女孩》的主人公是一个听力正常爱唱歌的女孩鲁比。这里为什么强调听力正常呢?因为她的父母和哥哥都是聋哑人,家里只有她自己一个人具有听力。这个家庭以捕鱼为生,渔船通知响应,渔获交易,与人沟通等事情都是由她进行翻译来进行的。这个家庭很需要她。 她有去伯...
继续阅读 »

故事


《健听女孩》的主人公是一个听力正常爱唱歌的女孩鲁比。这里为什么强调听力正常呢?因为她的父母和哥哥都是聋哑人,家里只有她自己一个人具有听力。这个家庭以捕鱼为生,渔船通知响应,渔获交易,与人沟通等事情都是由她进行翻译来进行的。这个家庭很需要她。


她有去伯克利音乐学院面试的机会,这是她的梦想,本片就是主要讲述了她在梦想与家庭进行抉择的过程和家庭成员的看法、处理方式等。


被“嘲笑”


鲁比出生在聋哑家庭,可想而知,她的家人没有办法教她讲话,她的发声很难听,这遭到了她的同学们的嘲笑、欺凌。她每天凌晨三点便起床与家人一起捕鱼,有时会来不及换衣服,同学也会嫌弃她身上的鱼腥味,进行讥讽。


种种这些,让她幼小的心灵受到了很大打击,所以她害怕面对她们,同时也造成了她的自卑、敏感。


师生情


在报课程的时候,她选择了合唱课,因为她热爱唱歌。但是第一节课,老师让大家开唱的时候,她却逃避得跑出去了。后来和老师讲明因为自己得经历,不敢在同学面前唱歌,害怕被嘲笑。老师给了她鼓励,让她有了自信。


老师发现她的天赋,推荐她去伯克利面试,同时教她唱歌。


在家庭不同意她去伯克利学院时,对她进行惋惜。


友情和爱情


鲁比得闺蜜是她参加合唱团前唯一的好友,闺蜜帮她分担心事,支持她唱歌。


参加合唱团后,她又有了一个男性朋友,是她的二重唱的搭档,当然也发生了一些小插曲。这位朋友家庭也存在一些问题,他的爸妈关系不和,他选择唱歌也并不是自己本意。后来她俩互相了解,互谈心事。 成为了男女朋友。


亲情


这部电影主要还是讲解亲情的。


在得知鲁比想去读大学时,她的妈妈特别反对,她说,“她不能离开我,她是我的宝宝”,爸爸说,“可是她从来没有当过宝宝”。是啊,她从小就帮家里进行翻译,是这个家与外界沟通的桥梁。她这么小就承担了这么多。她的爸爸希望她去,但是这个家庭没有她是没办法运作的。她的哥哥在看到父母把鲁比当成最重要的沟通媒介时,他心事重重,他认为他是哥哥,这些事情他也是能做好的。


虽说她的妈妈开始不支持唱歌,但是在她要进行表演的时候还是送了她一条红色裙子。她俩谈心过程中,妈妈在生孩子时希望鲁比是聋哑人,因为妈妈怕如果是正常儿童的话,自己的聋哑会成为一个“坏妈妈”。 在闺蜜和鲁比哥哥讲述了鲁比唱歌方面的天赋后,他很希望她去参加面试。


她还是没有选择去面试。这是她想成全家庭,因为她知道家庭对她的需要。


一家人一起去看了她的表演,看着台下人的感动,鼓掌,落泪等行为,爸爸心事重重,回到家后爸爸让她为她又唱了一遍,在星空下,他摸着她的振动,感受歌曲。


后来一家人一起去参加了伯克利的面试。这是家庭成员对鲁比的成全。


总结


这是一部很感人的电影,故事的讲述行云流水,每一个转折恰到好处。能够让我们聆听到悦耳的声音。


作者:随机的未知
来源:mdnice.com/writing/4a81248164b4409f8be55c27575fbf3b
收起阅读 »

勇闯天涯-程序员小哥哥,来婚介所试一下嘛(七千字长文预警!)

前言 今天技术博主不聊技术,聊聊生活聊聊情感。先叠个甲,我纯纯乐子人,对婚介所无任何恶意,可能后面还得用上,本次纯纯试探下婚介所是个什么路数!事件源于上周五的一通红娘电话,我一听要给我介绍有钱有颜的小姐姐,直接挂断,这天底下哪有这样的好事。当天下午的时候,又给...
继续阅读 »

前言


今天技术博主不聊技术,聊聊生活聊聊情感。先叠个甲,我纯纯乐子人,对婚介所无任何恶意,可能后面还得用上,本次纯纯试探下婚介所是个什么路数!事件源于上周五的一通红娘电话,我一听要给我介绍有钱有颜的小姐姐,直接挂断,这天底下哪有这样的好事。当天下午的时候,又给我来了一通电话,仿佛不知道我给她挂断了一样,基于一些奇妙的想法,我想尝试以及找找素材,我决定让她微信跟我聊。然后因为博主工作比较忙,打了招呼后,就没理她,最关键是到晚上下班后,我也忘了这档子事。周六的下午四点左右,一通电话开启了本次的故事,即使315曝光了相关产业,但是博主依然要冲,就是头铁。


阳光下午的微醺时光


接到电话的时候,我挺疑惑的,这次上来就问我现在是不是有空,出于礼貌,并且我也听出了她是昨天那个红娘,我就没有挂断电话。上来就说,弟弟,我是XX老师,今天来电话主要是聊一下,看能不能进一步推荐小姐姐。说她那里看资料我是97年的程序员,年收入XX,对吗?然后我说是,她就跟我说这里有个小姐姐挺合适的,北京XX工作的,身高165身高,本地的,收入XX。哥们一听就懵了,本地的,心里OS是,那咋遭得住,咱也不是高富帅,纯纯普男。红娘一听就问我有没有考虑常驻北京,然后就问我老家哪里的,我说四川的,她就在资料库里找了找,说真有个四川在北京的,快速给我念了一遍女生的资料。


接着就离谱了,问我怎么称呼?我说姓王,哪里工作,海淀XX公司?红娘直接薄纱,诶,没听过耶( •̀ ω •́ )y,咱们一般服务百度、阿里和字节的比较多。好好好,北京人中龙凤就是多,哥们就是菜中菜,脸都绿了。接着问我加班如何,公司福利啥的,然后说我这个181cm的身高在四川挺高的,她知道的四川男生都不太高来着。然后聊到了哥们的毕业学校,说前两天有个大连理工的女孩,真绝了,大家都这么爱走婚介所吗?我感觉聊到啥,都有女孩能配上,后面说到工作,又聊到一个大二的姑娘还没工作就来找对象了,好好好,走上了人生快车道。


然后聊到了我父母的职业,就说哥们的条件在当地不错,怎么没找上对象?我当时就说到了我的前对象,网恋的,就在掘金找的,一说到这个,好兄弟们,掘金真的能找对象的,不骗人。我的失败不是网恋的问题,纯属我自己的问题,第一次谈吧,不知道咋谈,自己也是摸不准进度,达不到对象的期待,慢慢地就淡了。我也是无脑纯爱战士,这是红娘听了之后的评价,哈哈,不过我觉得前对象确实挺不错的,当时要是硬扛着也能继续,但是我感觉可能是热情燃尽了,她也算是太忙了太累了,无论是生活还是工作,我都挺佩服,主动退出,我感觉应该是我被甩了。不后悔,男人就该当断即断,她也不小了,继续耗着,对她不公平。说远了啊,核心意思就是,网恋也有靠谱的,掘金这质量高的离谱,大家多去相亲角看看。


说着说着,突然红娘聊到了星座,说我应该了解了解星座,也说到了一些星座的小知识。然后顺嘴提到了应该门当户对,不只是能力,还有三观,阶层之类的。接着说道,我条件还行,为啥这么晚谈恋爱,是不是打游戏了?我说姐,没毛病,游戏真好玩!又接着问我单身多久了,身边还有没有介绍的呀,同事父母啥的资源。接着就进入正题了,就说小弟弟你呀,身边没有资源,姐姐这里有呀,你又有点慢热,男人花期这么短,这不得抓紧时间。你没谈就是没有遇到合适的人,圈子太小,北京这边初婚太晚了,25岁才准备开始,你想想四川重庆那边20左右就开始准备结婚了,你回去那就是大龄青年了,不是市场上最合适的那一批了。姐姐之前认识一个大哥,一年给女生花了七八万,环球影城去哈尔滨各种礼物砸下去结果手都没牵上。我???这不是大冤种嘛,移动ATM。红娘就跟我说,弟弟你啊,现在这恋爱能力,跟女生比划比划半年结果嘴都亲不上,咱们也不要浪费时间,选对人比胡乱去试强多了。姐姐我这啊,适合你的资源还蛮多的呀,你是B站来的资源,这种比较少,一般只占15%,我们婚介所大部分都是线下和国企政府合作的,所以需要你提供一定的身份和征信资料,因为我们这的姑娘都是认证过的,要对大家负责。接着又说觉得我性格比较好,很坦诚,就问我对女生有没有什么要求,我说年龄上不超过我三岁吧,不抽烟不去酒吧夜店,然后红娘跟我说,你这就没别的要求啦,那还挺低的,然后就问我三观、家庭情况之类的要求,问的很细。然后谈笑间,红娘给我猛推三个女生,嘎嘎读资料,听得哥们心里发慌,动不动就是大厂,家里有矿,问女生条件是否符合我的要求.......我真蚌埠住了,哥们真的配嘛,这条件谷歌,父母地方小领导或者开公司,问我符不符合,好好好,我能傍富婆不?


有一说一,专业红娘就是能聊,我俩聊了得有一小时,最后说让我去线下谈,给我预约了她明早10点半的时间。她想要了解下我这个人的衣着品位、谈吐举止、再做下深度的了解,以及一些信息的认证,同时也给我一些情感上的建议,让我少走些弯路。哥们听到情感上的建议,真的心动了,教练,俺就缺这个,确认了下这次聊天不收钱,就是个单纯的信息认证,我就决定去了。


小雨霖霖的春日午前


因为约好的时间是10点半,我住在石景山,婚介所在朝外SOHO那里,差不多一小时十几分钟的路程,我就九点出发了。到了地方之后,周围有好几个SOHO,没有明显指示牌,而且感觉周日早上那里人也少,当时就觉得奇怪了。因为事前的时候,跟亲友和群里的小伙伴下过军令状,不掏一分钱,实时播报进度,没消息就赶紧救我,所以我倒也没有特别慌。我的想法就很纯粹,想通过红娘的眼睛来认识我在相亲市场中是什么样的,因为我接触的人相对少嘛,所以也算是练练胆,特别是这种情感上的,多积累积累经验总没错。没找到地方,我就拍了个附件的标识给红娘老师,她就指挥我上了楼,上楼之后还蛮吓人的,左边黑的,右边就她家灯亮的。


进门之后有个助理来接待,给了我一张表单去填,相对详细哈,但是身-份-证这敏感信息可以选择不填,其实这会儿我觉得还挺不错,放下了防备,但是打开了录音,哈哈。把我领到一个逼仄的会议室,大概两平米吧,首先给我拍了一张坐着的照片,然后在我填表的时候,说要看下我的征信,简单点的就看芝麻信用就行,看了我的八百多分吧,就说你这还蛮高的。又试探性的问了能不能看下花呗借呗之类的,我寻思着也没多少额度,那就看呗,他一看就挺奇怪的,就说按你这个分数应该有好几万才对呀,你是自己调了吗?我说是呀,没事搞那么多干啥,又问我有没有信用卡,我说就拿花呗当信用卡。又说想看我支付宝里的资产,我寻思着没几个钱,那就看呗。他一看就说,你没炒基金股票啥的嘛,我说没,他就顺着话说,昨天有个姑娘和你一样,也是这样的,她就喜欢这种稳赚不赔的。浅聊了一下就说,去给我叫红娘老师,说红娘老师特别看重我,昨天周六来了好多姑娘,很多都不错的,让我跟红娘老师好好学学。哥们一听这个就来劲了,好啊,就是要这个,我不就缺这套恋爱情商嘛。


热情似火的夏日狂欢


红娘老师进来首先点评了我的头发,有点长还有点凌乱,说怎么还没理发呀。这一点说的挺对,我快一个月没理了,因为头发烫过,又有点长,显得乱。然后又说我好白呀,南方人皮肤就是好,因为我有痘痘嘛,就聊了聊油性皮肤。然后就跟我说想看看我短发的照片,说比较难想象我短发的照片,又说我这个是不是渣男锡纸烫,认出来了我这是前刺发型,感谢我的四川托尼,摩根前刺音容犹在。然后又说我字写的还不错,我说着就没必要硬夸了吧,她说跟其他人对比算是工整了。因为看到我手机壳了,就问我是个什么图案,我给她看了是二次元,她就问我是不是老爱玩B站,是不是博主,我说我哪是啊,只是喜欢看。她就说你声音还蛮好听的有点像肖战,可以整点视频啥的,说不定还能火。我说没那颜值,哈哈,谈笑间我就给她发了几张我的生活照,还有全身照片。她就说没有很胖呀,看着还好,而且家里还蛮干净的,弟弟习惯不错。


我也比较能说嘛,我就说红娘老师怎么不开个号啥的,吐吐槽啥的,比如B站上的XX说媒啥的。她跟我说她们上班很忙的,周一周二休息,平时都是快九点才下班,哪有时间开视频吐槽,都是朋友之间聊聊。然后她就很好奇我之前电话里说的前对象嘛,就聊了聊我前对象的事。因为我是抱着想要咨询的目的来的,所以我也说的相对比较详细,红娘比较在意的点是各阶段时间点、怎么认识的、告白怎么做的、准备了什么样的礼物和GG的理由。大致说了一遍,我觉得我前女友挺好的,无奈博主高攀不上,也没有达到人家的期望,就选择了默默退出。前女友说实话很不错的,情侣头像是我先换她才换的,我说话她也会回我,是我感觉被甩了,也是她有点冷吧,就放弃了。说这些呢,也是跟前面一样,说一下兄弟们要勇敢冲,掘金相亲角也靠谱,哪有那么多渣女,大部分还是好女孩,希望大家都把握得住,找到合适的另一半!


红娘老师跟我说了几个之前来聊的哥们,就说谈恋爱不能太晚,有一些大哥因为圈子比较小,导致来婚介所就想找个合适的姑娘一步到位。但是哪有这么合适的呀,一点攻略和目标都没有,怎么可能一口吃个胖子!我也附和老师说,对啊,心急吃不了热豆腐。然后就跟我说,昨天来了两哥们,一个京东一个百度的,还有00年来找对象的,我一听都懵了,这不都是人中龙凤嘛,这还愁对象,有没有大厂哥们来现身说法的,让小弟我长长见识。聊着聊着,就跟我看了个小姐姐,大四左右吧,想找个大五岁左右工作稳定的哥们,本身条件很优秀的,北交大硕士进国企,所以想要个稳定的生活。反正红娘老师意识就是说,现在女生吧,恋商普遍比男生多个三五年,现在这么卷,考虑得都比较现实。然后就说现在女生都是要求有钱有颜,小弟弟你也没钱,正在发展期嘛,颜的话还算周正,需要打理打理。然后就说想看看我之前的照片,要看我手机,emmm,这时候我没发现这是个套路,应该之前有哥们也做过这事儿。我有开录音嘛,左上角有小标,很烦,红娘应该是特意盯了这个地方,一开始问我怎么不给她看手机,而是直接发给她。我也没在意,她就老找理由看我手机,然后我也不小心被她看见了,她就问我是不是忘了关导航,哈哈,我打了个马虎眼就过了,然后后面过了一阵又看到了,就直接问我是不是录音。我非常坦诚的告诉她就是在录音,有顾虑,然后我也当着她面关了,我俩嘻嘻哈哈也就把这事过了。


想要摸一下秋天的老虎


聊了聊我的家庭,跟我聊了聊她最近咨询过的男生,有成功也有失败案例,反正都是会员。比较隐晦地指出了我这个水平在北京不够看,在成都也不算特别优秀地类型,但是结合家庭和年龄来讲,也算是还不错,至少还有操作空间。我一开始就想知道我在婚恋市场是个什么档次,以及从红娘视角来看我是什么样的,所以我就直球问她了。或许是基于职业素养,或者我问的有点子收费味道了,她顿了一下,从两方面给了我建议,一是从我初恋这段历程总结出来的,说我就是没有技巧的纯爱战士,需要提高情商,反正套话居多。二是不要乱撒网,要精准定位,选择自己合适的人,基于星座啥的跟我聊了半天,我这金牛座适合什么样的人。然后就说我这个改是来不及了,27也不小了,没救了,就从选对人开始,然后就开始围绕她们的服务开始聊。


总共聊了得有三小时左右吧,前一个半小时唠家常,根据你的资料聊细节,时不时说说女生的资料。后面就开始猛攻,围绕中介所的两项核心服务,一是心动女生匹配筛选,二是全程跟踪指导,结合真实案例开始跟我介绍。比如女生这个,真的是拿了五六份女生的资料,就跟简历似的,问我有没有眼缘,又跟我说这几天来了什么什么姑娘,有还没毕业的,有点子真实案例掺点焦虑的感觉。比如全程指导,给我看了她手下成功的案例,放了点截图和视频啥的,让我看效果。


中间插一下哈,聊聊我对红娘的看法,真的很强。能干这行的都是社牛,还有很强的气场,我确实能感觉出来她是很快乐地在撮合,觉得是在做正确的事,收的钱理所应当。说真的,要不是我去之前就抱着分文不出的想法,她一顿吹我真给了,业务能力太强了。她聊天的话,目的性很强,总是往婚介服务,这个筛选方向去带,会弱化你的劣势,不会很明显地贬低你,但也不会特别夸耀你的长处,就把你当作一个朋友一样,所有都是围绕我们能给你找一个天造地设的对象这一核心点展开。说实在的,动不动认个亲弟弟这操作也太骚了,见面第一次,这社交强度直接拉满,很热情。


聊聊收费啥的,好像每个人都不一样,给我的标准是1年49990,半年29990,3个月19990,后面我说不用了,拉扯半小时,认我做亲弟弟,然后给我亲属价对赌协议,先交10100等成功了再补9890或者给她介绍2个就不用给尾款了。最后博主一是领导在催干活,嘎嘎电话,朋友在催吃饭,也微信电话不停,就想润了,红娘就说要不先交500定金,不行再退,我确实没这想法,就发了50红包给姐买奶茶。反正这吃相一出来就有点尬住了,我这确实是很好说话,没有一甩脸子直接走了,就这么耗着。说实在的,我确实觉得人家说了3小时,这总得有点收益,50块钱在北京不是什么大钱,但是我本来也是抱着聊聊的想法,没想到上来就这么狠,直接2W起步,真恐怖,润了润了。


又到了白色相簿的季节


最后聊聊博主的收获,有用信息不多哈,大部分是一些套话,这大概就是免费内容吧。她给我看了客户的跟踪记录,红娘会全程指导男生的行为,会推一些书或者情感内容啥的,当然,这都是收费内容。怎么说呢,这一次三小时的激烈battle,我也能感觉出来,我还是该在情商上做一些提升,红娘有提到男女之间的情商和朋友之间的情商是两码事,说我上一次挂了就是技巧不足,竟然半年连嘴都没亲,这还是人???跟我说她们那里的都是一个月速通,我这样的已经没救了,好好好,这年头纯爱战士就是鲨BEE。


我其实对这家婚介所没啥意见,我也是想着既然聊上了那就去看看呗,没想到第一次这强度就这么大,哈哈,离谱。我看了下女生资源都很不错,男生也很厉害,都是人中龙凤,不知真假。XX爱恋,她跟我说主要还是线下,我的资料是从B站过去的,就离谱,不知道我填啥了,一开始就知道我的性别年龄和手机号,其他一概不知,可能是我资料被卖了吧,根据年龄给我推送的。喔,对了,说是每周给政府或者国企办公益相亲会,我之前倒是没怎么了解,不知道她家是不是在北京属于厉害的了,还是纯诈骗,摸不清楚,这也是我没交钱的理由之一。因为我在B站上看过XX说媒嘛,我就问她,怎么不开个自媒体号吐吐槽,还能挣点外快。哈哈,这姐非常真实,说剪辑、化妆、文案太累了,线下就够赚了,没必要混线上。


写着写着,突然想起来这姐还说过我一个坏毛病,说我没有底线,有点舔狗,女生一般不喜欢姿态放低的男生,希望我有点神秘感,或者说装一点。哈哈,下一个更好,咱们有的是资源,看得出姐是相当洒脱,成年人不改变只选择这话倒是诠释的清清楚楚。还说我应该有个底,不要一上来就跟人托底,比如她一看我就是个逗比的人,结果跟我一聊还真是个嘻嘻哈哈的乐天派,这样就没有神秘感,她说女生一般不太喜欢这种。


最后的最后,她把经理叫来了,做个回访,我是很欣赏红娘老师的,因为我这次没谈成业绩我也是相当抱歉,所以当着经理面说了很多红娘的好话,没有谈成也确实是我的问题。哈哈,经理直接问我,免费给我介绍同意不,我都懵了,这太狠了,我也没答应,这种形式还是太超前了。相亲说实话还是摆条件,看见女生资料搁面前一遍遍刷,人中龙凤太多啦,哈哈,不由得想起了我初恋也就是我前对象,我也得好好努力呀!


锵锵!我闪亮登场!


今天突然想到,好像真是在B站一个UP那里填过资料的,是我错怪人家了。红娘这姐姐挺有意思的,我是真的觉得她干这行很快乐,她还问我对这行有没有兴趣,哈哈。这种撮合有情人就能收钱的事可太行了,我也蛮喜欢这种做好事的感觉。不过骗人的也不少,315曝光过了,大家也长个心眼吧,学会识人。


最后做个总结吧,博主从昨年开始琢磨男女大事,经历了人生第一次相亲会、初恋、婚介所,虽然都只有一次,但都是挺有意思的。哎,母胎SOLO真的太难了,不会谈啊,盲目冲锋的纯爱战士真的不是版本答案了,红娘老师也跟我说,女生感情上比男生早熟三四年以上,难难难,但是博主依旧对生活抱有期望,哈哈,毕竟我是个乐子人。


我的人生信条是,我要让这痛苦压抑的世界绽放幸福快乐之花,向美好的世界献上祝福!!!


作者:云雨雪
来源:juejin.cn/post/7350123500936986674
收起阅读 »

祖传屎山代码平时不优化,一重构就翻天覆地

写作背景 写背景之前先放一张网图,侵删。 有一个活跃应用包含了2个相似业务场景,所以共用了底层模型。 前期在开发过程中,强行将两波研发组正在研发的产品底层模型和能力统一。底层能力统一遇到了挺多问题,比如数据库字段适配、转换、冗余;repo 层 SQL...
继续阅读 »



写作背景



写背景之前先放一张网图,侵删。



image.png


有一个活跃应用包含了2个相似业务场景,所以共用了底层模型。




  1. 前期在开发过程中,强行将两波研发组正在研发的产品底层模型和能力统一。底层能力统一遇到了挺多问题,比如数据库字段适配、转换、冗余;repo 层 SQL 条件拼接用了大量 if else,导致建索引困难…等等。

  2. 一些历史原因,该应用经手了十多个研发,代码是垒了又垒,出现一个很有规律的现象,大家都是只增代码不减代码。

  3. 代码性能随着数据规模增加不断降低,靠着优化补丁缝缝补补支撑着,业务高峰期经常被运维同学拿着 SQL 光顾。



重构该项目想法不止10次,想逮着机会拉着各方大佬商讨重构事项,因为重构对业务是没有收益的,并且重构难度相当大,所以迟迟没有下定决心。


最近刚好产品需要打磨下一个版本,需要挺长时间,几个后端研发商讨要不重构吧。嗯,我想可以,于是我找上前端负责人沟通拉他入伙,找上前端之前测试已经同意了。


于是一场重构拉开序幕了。




  1. A 同学负责梳理和收敛模型、数据订正、向上提供能力。

  2. B 同学负责梳理前端接口,编排底层能力,提供原子接口给前端(最复杂,直接面向Web端业务,接口有很多特殊逻辑)。

  3. C 同学负责引擎层,和一些计算类逻辑,另外就是打打杂。



重构


大型重构耗时不说还费人力,搞不好重构完你拿不到业务结果,所以重构前你要明确收益是啥?无非就是下面几种




  1. 性能提升产品体验更好;

  2. 简化架构并提升架构扩展性(后面迭代基于重构后架构能快速开发上线);

  3. 历史债清理,历史代码可读性差维护费劲(大部分程序员看别人代码都是这样吧)。



我们是三种情况都中,下面简单总结重构的思路吧。


模型梳理和能力收敛


底层模型我认为最重要,要可靠、稳定且变动少,如果在迭代中你的模型变来变去,上层业务根本开发不了或者边开发边改,到项目收尾就是另一坨屎山。


上层业务是根据底层模型长出来的,所以一定要跟产品讨论确定最终模型,若有好的竞品参考更好了,你的设计可能会看的更远,以防过度设计,架构设计满足未来1-2年迭代即可。


模型设计需要预估数据规模,数据规模决定是否采用分库分表/分区表。如果不好预估采用简单原则先上线看看业务效果,但基础框架这些能力一定要预留好,上量后能快速开发上线。


底层模型和能力收敛了,上层业务编排对能力的复用性更高。ps:这次模型梳理我们干掉了 2 张千万级表。


数据订正


模型梳理和收敛一般会涉及数据订正,特指线上模型对应的数据割接在新模型。一般会有下面几种方式




  1. 写脚本从数据库捞数据订正数据,一般会先 select 查询到内存中,重新组装数据再 insert 新模型。数据量小场景完全可行,但数据量大是跑不动(已踩过坑,线上数据几天没跑完最后发布失败)。

  2. 写 SQL 直接操作数据表,简单的数据处理场景、数据量小场景可行,数据量大场景不可靠,容易超时并且会有数据库稳定性风险,另外订正逻辑复杂是搞不定的(已踩过坑,线上跑数据失败导致发布失败)。

  3. oplog、binlog.... 日志采集同步到消息队列(kafka、pulsar 等),启消费组消费订正数据(我最常用也是最可靠的),数据量大的场景特别爽,处理存量数据的同时还能保证增量数据同步处理。



数据订正是清理过期数据最佳时期。假若平台过期数据体量大,这部分数据不迁移新表,留在历史表中当备份就行,亦可快速恢复。ps:本次重构过期数据预估是千万级别。


API 接口


接口是你对外的门面,应该提前规划明确,不能新增需求就干一个接口,需求迭代到后期,大大小小接口加起来几十上百个维护成本是很高的。


我们一般会按照下面几个原则:




  1. 按操作分类比如:增、删、改、查是一类,只会定义4个接口上游业务方调用需传入 source 区分调用源。

  2. 接口保持简洁,不耦合非当前业务的复杂数据。比如业务上需要回显组织架构数据(员工名称、部门、员工上级等),这类数据需要业务方自行编排组织架构 byids 接口。

  3. 接口具备降级能力,不能因为接口内部编排的非重要接口、逻辑报错导致整个接口不可用。
    降级指将某些业务或者接口的功能降低,可以是只提供部分功能,也可以是完全停掉所有功能。



这次重构 B 同学和前端面临了巨大压力,接口多、混乱、逻辑不清晰,决定梳理业务逻辑按照上面 3 个原则重写接口。


代码重构技巧


代码重构也是本次重构重点,经过长时间迭代已经闻到了坏代码味道。怎么重构早就心中有数,很早就盘点和推演了,下面是我常用的一些重构技巧,这些技巧都是非常经典的,如果看过「重构改善既有代码设计」应该都不陌生。


内联临时变量

项目里有一些临时变量,只被简单赋值了一次。将这些临时变量的赋值语句直接嵌入到使用它们的地方,而不是创建一个新的变量来存储这个临时值。


func Publish() error {
// ... 省略一部分代码
err = Producer(context.TODO()).ProducerOne(&obj)
if err != nil {
return err
}
return nil
}

临时变量内联改造后👇👇👇


func Publish() error {
// ... 省略一部分代码
return Producer(context.TODO()).ProducerOne(&obj)
}

魔幻数字"(Magic Number)

指代码中使用未经解释或定义的常数值,这些值通常没有命名并且没有给出其含义或用途。这样的数字使代码难理解和维护,项目里面很多魔幻数字使用。


func Update(ids []string, nodeID string) {
// ... 省略一部分代码
Report(context.TODO(), nodeID, "6", ids)
}

要解决魔幻数字比较简单,只需你把业务逻辑理解定义成枚举就可以了,这个数字6表示朋友圈类型,魔幻数字改造后👇👇👇


type TargetType int

const (
QWMoment TargetType = 6
)

func Update(ids []string, nodeID string) {
// ... 省略一部分代码
Report(context.TODO(), nodeID, QWMoment, ids)
}

删除注释、未引用代码「俗称死代码」

根据我 review 代码的经验,不少研发同学会把已注释、未引用代码保留,这部分代码是非常影响后面维护者思路的,我们在重构过程中遇到不少这类代码,来来回回找测试和研发确认为什么会保留,哪些业务常用在用?带来了不小负担。(尤其是越上层的死代码引用了一堆下层代码,比如controller 引用 service,service 再引用 repo ,若重写 repo 非常上头)


所以我强烈建议,一旦代码不用了,应该立刻删除。若删除这部分代码后面迭代可能会使用,我建议重新开发。我列一些删除代码后的收益。




  1. 清晰度和简洁性;

  2. 减少维护成本;

  3. 减少冗余和混乱;

  4. 避免误导。



卫语句取代条件表达式

卫语是用来提前结束方法执行的结构。通常情况下,卫语句用来检查某些前置条件是否满足,如果条件不满足,则立即退出方法执行,以避免进入后续的代码块。有助于减少代码嵌套深度,增加代码的可读性和可维护性。


按照我的经验,卫语句应该有下面 2 种情况:




  1. 两个条件分支都属于正常行为;

  2. 有一个条件分支是正常行为,另一个分支则是异常的情况。



我们review过的代码一般是第二种情况比较严重。


func Recall(exclusion constant.ExclusionType)error  {
if exclusion == constant.OnlyOneExec {
if detail.TargetID == "" {
return nil
}
_, err := repo.Update(ctx,....)
if err != nil {
return xerrors.Wrapf(err, "Update")
}
}
return nil
}

调整后代码👇👇👇


func Recall(exclusion constant.ExclusionType)error  {
if exclusion != constant.OnlyOneExec {
return nil
}

if detail.TargetID == "" {
return nil
}
_, err := repo.Update(ctx,....)
return err
}

变量改名

好的命名能让读者一目了然,变量名可以很好的解释一段代码干了什么。我发现项目里面很多字段名、类名、包名很模糊,很难理解具体的业务(包括我自己也经常命名错)。


下段代码是我整理的坏的命名


TaskCommand 是 Kafka 消费者依赖的实体,收到消息后根据 Type 和 Status 撤回数据。但你看 struct 名 跟撤回没有任何关系。


// TaskCommand 任务相关命令
type TaskCommand struct {
Type   int8 `json:"type"`   // 执行类型
Status int8 `json:"status"` 
}

所以我选择把 TaskCommand 替换成跟业务更贴切的名称👇👇👇


type RecallDataParam struct {
Type   int8 `json:"type"` // 执行类型
Status int8 `json:"status"`
}

引入参数对象

以一个对象取代一些参数,可以改善代码的可读性和维护性,尤其是在函数参数列表较长或者参数之间存在复杂关系的情况下。将一组相关的参数封装到一个对象中,将该对象作为函数的参数传递,简化函数签名并提高代码的清晰度。


在一些历史比较久的代码里过长参数真的很常见,从 controller 透传到 service 再透传到 repo 层,代码复用性也非常低。


type AppImpl struct {
}

func (app *AppImpl) List(tp []int, status, page, pageSize int, keyword string, domain string) ([]interface{}, error) {
// .... 省略业务逻辑
return nil, nil
}

上段代码我一般会在 controller 和 service 中间抽一个 dto 实体。👇👇👇


type AppImpl struct {
}

func (app *AppImpl) List(listDTO *ListDTO) ([]interface{}, error) {
// .... 省略业务逻辑
return nil, nil
}

type ListDTO struct {
tp []int
status, page, pageSize int
keyword, domain string
}

提炼类

一个类应该是一个明确的抽象,它的职责是单一的,只处理一些明确的职责。


提炼类一般是下面两种情况




  1. 需求是在不停变化和累加,你会这儿加一个函数,那儿加一个方法。导致某些文件或者类非常臃肿。

  2. 相似的能力,散落在不同的业务板块,涉及的开发都在重复建设,有一个需求建一个烟囱。



典型案例是项目中事件上报能力,本应该是一个通用能力集中收敛上报代码,据我梳理代码散落在多处,上报触点有 10 来个,每个触点都在写同样的上报代码,假设某一天上报逻辑变化必须在这 10 多处做出许多小修改。


所以我决定把上报能力收敛在一个类,将复杂逻辑封装到该类,定义有限参数露出给使用方。


上报通用能力封装在 EventTracking。👇👇👇


// Tracker 埋点上报接口
type Tracker[T any] interface {
EventTracking(in T) error
}

type CMSReachDTO struct {
}

type CMSReachTracking[T any] struct {
ctx context.Context
}

func NewCMSReachTracking[T any](ctx context.Context) Tracker[*CMSReachDTO] {
return &CMSReachTracking[T]{ctx: ctx}
}

func (t *CMSReachTracking[T]) EventTracking(in *CMSReachDTO) error {
// ....逻辑省略

return nil
}

提炼超类

如果两个类在做相似的事,可以利用基本的继承/组合(GO 只有组合)机制把它们的相似之处提炼到超类。一般会把字段、方法都搬移过去。


我遇到的 case 在 entity 上会多一些,比如下面这两个 struct。


type Task struct {
ID string `gorm:"column:id"`
Tenant string `gorm:"column:tenant"`
SubDomain string `gorm:"column:sub_domain"`
IsDel int8   `gorm:"column:is_del;default:1" `
CreateAt int64  `gorm:"column:create_at;autoCreateTime:milli"`
UpdateAt int64  `gorm:"column:update_at;autoUpdateTime:milli"`
CreateUserID string `gorm:"column:create_uid"`
UpdateUserID string `gorm:"column:update_uid"`
// ... 省略其他字段
}

type TaskDetail struct {
ID string `gorm:"column:id"`
TargetID string `gorm:"column:target_id"`
Tenant string `gorm:"column:tenant"`
SubDomain string `gorm:"column:sub_domain"`
IsDel int8   `gorm:"column:is_del;default:1" `
CreateAt int64  `gorm:"column:create_at;autoCreateTime:milli"`
UpdateAt int64  `gorm:"column:update_at;autoUpdateTime:milli"`
CreateUserID string `gorm:"column:create_uid"`
UpdateUserID string `gorm:"column:update_uid"`
// ... 省略其他字段
}

上面这段代码他们都有共性的代码,并且我非常熟悉业务是不可能更改的,所以我会提炼一个超类。👇👇👇


type SuperParty struct {
Tenant string `gorm:"column:tenant"`
SubDomain string `gorm:"column:sub_domain"`
IsDel int8   `gorm:"column:is_del;default:1" `
CreateAt int64  `gorm:"column:create_at;autoCreateTime:milli"`
UpdateAt int64  `gorm:"column:update_at;autoUpdateTime:milli"`
CreateUserID string `gorm:"column:create_uid"`
UpdateUserID string `gorm:"column:update_uid"`
}

type Task struct {
ID string `gorm:"column:id"`
SuperParty
// ... 省略其他字段
}

type TaskDetail struct {
ID string `gorm:"column:id"`
TargetID string `gorm:"column:target_id"`
SuperParty
// ... 省略其他字段
}

当然某些场景还有一些配套的方法,也可以一并搬迁到 SuperParty 里面。


提炼方法/函数

提炼函数/方法是我常用的一种手段,我不喜欢长函数/方法。我看过一个说法,一个函数/方法应该能在一屏中显示,我一直奉为经典语录(我写的代码函数/方法基本不会超过一百行);另外只要有一段代码不止被用一次,我就会把他们单独放进一个函数。


有这样一个场景,调用外部 byids 查询员工信息获取 externalId 执行业务逻辑,封装外部接口调用。


type Client struct {
ctx context.Context
}

func (c *Client) GetByIDs(id []string) ([]*User, error) {
// ....省略业务逻辑
return []*User{}, nil
}

type User struct {
ID         string `json:"id"`
ExternalID string `json:"externalId"`
}

下面是业务方使用 GetByIDs() 方法


func TestGetUserByIDs(t *testing.T) {
ids := []string{"1""2"}

client := &Client{}
users, err := client.GetByIDs(ids)
if err != nil {
panic(err)
}

l := make([]string0len(users))
for _, v := range users {
l = append(l, v.ExternalID)
}

// ...执行业务逻辑
}

 业务方调用 GetByIDs() 方法,遍历 users 获取 ExternalID 执行业务逻辑。在业务上这种操作还真不少,所以决定优化复用一部分代码。👇👇👇




  1. 定义 Users 切片。

  2. GetByIDs() 方法返回 Users。

  3. Users 提供 GetExternalIDs 方法。



type Client struct {
ctx context.Context
}

func (c *Client) GetByIDs(id []string) (Users, error) {
// .... 省略业务逻辑
return Users{}, nil
}

type Users []*User

func (u Users) GetExternalIDs() []string {
out := make([]string0len(u))
for _, v := range u {
out = append(out, v.ExternalID)
}

return out
}

type User struct {
ID         string `json:"id"`
ExternalID string `json:"externalId"`
}

下面是业务方使用 GetByIDs() 方法


func TestGetUserByIDs(t *testing.T) {
ids := []string{"1""2"}

client := &Client{}
users, err := client.GetByIDs(ids)
if err != nil {
panic(err)
}

l := users.GetExternalIDs()
// 执行业务逻辑
   // ....
}

代码空行

我非常非常不喜欢代码从头到尾写下来没有任何空行,难以阅读让读者很难提起兴趣。空行在我看来是必不可少的,在代码中使用空行来分隔不同功能或逻辑块之间的代码,空行使得代码更易读。


下面段代码是没有任何空行的,代码比较短阅读起来可能并不费劲。
image.png


适当进行空行优化后👇👇👇
企业微信截图_25861264-b69d-48eb-bd5c-eb2e4e9f87aa.png


上段代码先不关注逻辑,优化后可读性更强了,代码分为3段逻辑,每段逻辑都有各自的职责。


空行是用来区分不同逻辑块的,过度空行也会影响代码阅读,如下:
image.png


引入设计模式

设计模式是被大佬们验证过的、开发经验的总结,可以帮助我们更好地组织和管理代码,并提高代码的可维护性、可读性、可扩展性和可重用性。下面链接是我最常用的设计模式,也在这次重构过程中全部用上了,有兴趣可以看看。


最后总结




  1. 如果你的项目不是外包项目(交付了就完事儿),一定要多回头看看自己写的代码,跟着版本迭代持续优化和改进,你才能进步。另外对代码一定要有洁癖。

  2. 重构是持续的过程,如果是重要项目,每个版本我们都会推进代码优化,保证代码可维护性、可扩展性、另外就是高性能。千万别堆积最后,那可是大工程到后面很多人是没有决心干这个事儿的,所以大家应该平时迭代中不断优化和完善,才可持续性。

  3. 大型重构时,一定要明确收益并且是可量化的,比如重构后 qps 提升了10%,应用消耗资源降低了…等等,你才有跟老板谈判的筹码。



作者:彭亚川Allen
来源:juejin.cn/post/7344290391989485578
收起阅读 »

业务开发做到零 bug 有多难?

大家好,我是树哥,好久不见啦。 作为一个工作了 10 多年的开发,写业务代码总是写了不少的。但你想过做到零 bug 吗?我可是想过的,毕竟我还是有点追求的。不然每天都是浑浑噩噩地过,多没意思啊。 大概在一年多前,我给自己立下一个目标 —— 尽量将自己经手的业务...
继续阅读 »

大家好,我是树哥,好久不见啦。


作为一个工作了 10 多年的开发,写业务代码总是写了不少的。但你想过做到零 bug 吗?我可是想过的,毕竟我还是有点追求的。不然每天都是浑浑噩噩地过,多没意思啊。


大概在一年多前,我给自己立下一个目标 —— 尽量将自己经手的业务需求做到零 bug。不试不知道,一试吓一跳,原来零 bug 还真的还不容易。今天,树哥就跟大家分享关于「业务开发零 bug」的一些思考。


要做到业务开发零 bug,其实挺难的。这涉及到非常多方面,有些方面可能还不只是你能控制的,例如:产品 PRD 详尽程度,产研组织的稳定性等等。经过一段时间的思考与摸索,我自己总结出一些影响因素,分别是:



  1. 产品需求文档的清晰程度

  2. 需求的复杂程度

  3. 开发人员的细心程度

  4. 开发人员是否详细自测过

  5. 开发人员对项目的熟悉程度

  6. 开发人员开发时间是否充足


针对上面说到的影响因素,我们一个个详细聊聊。


需求文档清晰程度


对于研发、测试人员来说,他们获取信息的源头就是产品的 PRD 文档。因此,需求文档是否写得清晰、明确,就显得非常重要。


如果产品自己对功能都不了解,那么输出的需求文档肯定「缺斤少两」,到时候就是边开发边补充需求,甚至是在测试过程中补充需求。遇到这种情况,想要做到零 bug 真的非常难。


因此,清晰明确的需求文档,是我们实现业务开发零 bug 的重要前提。如果这个前提保证不了,那要做到零 bug 真的很难。毕竟想做成啥样都不知道,程序员又不是神仙,咋能猜出你想要什么。但这块内容,更多是对于产品人员专业能力的要求,开发人员无法控制。


在一些公司,会再需求评审之前先对需求文档进行一次初审,筛除那些有明显重大问题的需求,这样可以减少一部分劣质需求。


但初审的作用还是有限的,它没办法对功能的细节做较多的判断。很多时候恰恰就是一些功能细节的缺失,导致了一些 bug 的诞生。


需求的复杂程度


需求的复杂程度,对于实现业务开发零 bug 也有很大的影响。举个简单地例子:一个改文案的需求,和一个完全重新做的功能。


这样的两个需求,其复杂程度差别很大,肯定是改文案的需求实现业务开发零 bug 的难度低很多。对于一个完全重新做的功能,要做到完全零 bug,对于开发人员的要求非常高。


对于越复杂的项目,零 bug 的可能性就越低。因此,很多项目为了追求产出功能的高质量,会采用将功能点拆得非常细的方式,来减少单个需求的复杂度。


笔者公司在去年做过这个尝试,确实是可以较大地提高产出功能的质量。


细心程度


前面说到需求文档的清晰程度很重要,这取决于产品人员对于业务的理解程度,以及对于对于功能的熟悉程度。开发人员的细心,就像是一个质检关卡一样,在开发之前就对产品的需求内容进行详尽的思考与提问。


对于粗心的开发人员来说,其可能不看需求文档就直接参加需求评审,等到开发的时候边写代码边看需求文档,其写得代码也是一边熟悉需求一边改。这样写出来的系统功能是比较差的,没有一个统一、全局的设计与思考,很容易在细节处发生问题。


一个细心的开发人员,其会在评审之前就详细阅读需求文档,甚至会前前后后翻阅好几次。他甚至会逐字逐句地阅读,弄懂每个文字、句子的意思,甚至有时候会让你觉得他是在玩文字游戏(但不得不说,确实有必要细致一些)。


最后会联系上下文思考功能的合理性。如果发现一些不合理的地方,他会积极与产品沟通反馈,以确保其对于需求的理解,与产品经理对于需求的理解是一致的。


通过对比,我们知道细心的开发人员对于产品经理来说,是一个莫大的帮助,可以帮助他查漏补缺,让其对于功能的考虑更加细致、严谨。


这里的开发人员不仅仅指的是后端开发人员,也包括前端开发、移动端开发,他们都会从不同角度提出问题。


对于后端开发人员来说,他们可能会提出性能问题。对于前端开发以及移动端开发同学,他们可能会提出交互问题、样式统一等问题。


简单地说,细心的开发人员可以弥补需求文档的缺陷,从而让大家对于需求的理解更趋于一致,从而减少 bug 的发生。因此,开发人员的细心程度也是决定业务开发能否实现零 bug 的关键因素!


是否详细自测过


即使写过 10 多年代码的开发人员,刷 Leetcode 也不敢说 bug free 一把过,对于更加复杂的业务代码更是如此。因此,要做到业务开发零 bug,其中一个很重要的操作便是 —— 自测。


自测可以帮你再次检查可能出现的问题,从而提高零 bug 的概率。对于我而言,我习惯性在自测的时候再次对照一遍需求文档,从而避免自己遗漏一些功能的细节点。


对于自测而言,业界有很多种自测方法,包括:单测、集成测试、功能测试。一般情况,建议自己选择适合自己的自测方法。


很多时候,功能测试是相对来说性价比较高的方式。除此之外,自测的详细程度也根据实际情况有所不同,例如有些人只会测试正常情况,但有些老手会测试一些边界情况、异常情况。


毫无疑问,你越能像测试人员一样测试,你的提测质量肯定就越高,bug 当然也就越少。


对项目的熟悉程度


这里说的项目熟悉程度,既指技术层面的熟悉程度,也指业务功能层面的熟悉程度。


技术层面的熟悉程度,指的是项目之间是用什么技术栈搭建的,你对这些技术是否都熟悉。举个很简单的例子,项目中采用了微服务的方式进行调用,那么你是否清楚是什么微服务调用?


如果采用了 ElasticSearch 进行搜索,那么你是否对 ElasticSearch 有一些了解,知道一些基本使用及最佳实践?等等。


这些算是技术层面的熟悉程度,你对这些越熟悉,你在技术层面发生问题的可能性就越小。


业务功能层面的熟悉程度,指的是你对项目其他模块的业务是否熟悉。例如你经常负责 A 模块的功能,你对 A 模块肯定很熟悉。


但下个迭代你就要去做 B 迭代的需求了,这时候你肯定不是很熟,相对来说出错的可能性就更大一些。


无论是技术层面,还是业务层面的熟悉程度,都会随着你做了更多的需求,变得更加熟悉。到了后面某个阶段,你基本上就不存在踩坑的问题了,也为你业务开发零 bug 奠定了基础。如果你是一个刚刚进入公司的新手,那么做到零 bug 还是很难的。


开发时间是否充足


开发时间是否充足,决定了你是否有充足的时间去熟悉需求,去和产品经理确定细节。有了充足的时间,你也才能有一定时间去进行更详细的自测。更为关键的一点,有充足的时间,你写代码才能写得更好。因此,开发时间是否充足是很重要的。


在实际的开发过程中,会因为各种各样的原因,其实并没有办法给你留出特别理想的开发时间。这时候该怎么办?有些人选择接受,去压缩自己的时间。


有些人则会选择去沟通,或者协调资源,保证自己有充足的时间。其实,正确的做法还是第二种,这样会更好一些。


这需要开发人员有更强的综合能力(沟通、协调能力),但并不是每个开发人员都具备的。关于这点,又是可以聊的一个话题 —— 当你的需求被压缩工时的时候,你应该怎么做?这里暂不展开,后续有时间可以聊聊。


简单来说,开发时间是基础,没有合理、充足的时间保障的话,要做到业务开发零 bug 是不可能的事情。


总结


要做到业务开发零 bug,其实就是要消除功能开发过程中的所有不确定性,包括:需求功能的不确定性、自己写错代码的不确定性等等。而发生这些不确定性的地方,可能就有:



  1. 产品需求文档的清晰程度

  2. 需求的复杂程度

  3. 开发人员的细心程度

  4. 开发人员是否详细自测过

  5. 开发人员对项目的熟悉程度

  6. 开发人员开发时间是否充足


除了上面说到的 6 个影响业务开发零 bug 的因素之外,肯定还有其他影响因素。


你能想到什么影响业务开发零 bug 的因素吗?欢迎在评论区留言与大家分享。


好了,今天的分享就到此为止,希望大家都能做到业务开发零 bug,业务开发代码一把过!


如果你觉得今天的文章对你有帮助,欢迎点赞转发评论,你的转发对于我很重要,感谢大家!


作者:树哥聊编程
来源:juejin.cn/post/7347668702029971475
收起阅读 »

职场上的人情世故 - 初入公司的第一个项目

说下背景 来公司的第二周,上面下发了新需求,也是我参与公司的第一个项目。 我先说下公司一个项目的大体配置 产品经理 1~2人 一般中小版本就1人 UI 1~2人 研发前端 1~3人 研发后端 1~5人(包含协同团队) ps:其中后端中1...
继续阅读 »

说下背景


来公司的第二周,上面下发了新需求,也是我参与公司的第一个项目。


我先说下公司一个项目的大体配置


产品经理 1~2人  一般中小版本就1人
UI 1~2人
研发前端 1~3人
研发后端 1~5人(包含协同团队)
ps:其中后端中1人为项目负责人,负责整体项目进度和协调资源
测试 1~2人

好的,故事由此开始。先铺垫下,该项目是我从业以来最无力最绝望最想扯呼的一个。


需求评审


周一刚来公司,就被公司给我安排的导师L 叫到身边


导师L:「一会儿有个需求评审,我文档先发你,你先抓紧时间看看」


懵懂的我:「好的,我先熟悉下任务」


说实话文档看起来真的有点头疼,主要是上面的一行字我真的无语至极【与线上保持一致】。公司的项目还是比较大的,我上哪儿去了解保持一致是个啥意思......问下导师吧,他也在排查线上问题;问下其他同事吧,也刚来没多久不了解这块业务....


好吧时间应该够,我先打开系统,看看这功能到底在哪里。


「走,A2评审会」 导师L给了我一个眼神


大哥,我才看了不到20分钟,功能我都没看完......


我的情况稍微有点特殊,一般来说,大家跟随导师的节奏,问题都不大
看不懂的需求,一定要整懂了在动手,否则返工风险很大
时间不允许?那要再考虑下该公司是不是适合你了哦!!!总不能说能跑起来就行吧

过程我全程梦游,大家都在提问题:各种数据的兼容方案、功能冲突怎么兼容、有类似功能是否能套用、数据权限是否考虑、特殊逻辑的兜底方案.......


开始还能记一下笔记,后面发现 跟不上,根本跟不上 直接 弃笔,从容 面对现实了


从会议室走出来,嗯~~ 怎么形容心情呢。我高考语文作文那一页名字忘了写出考场都没这么忧虑过(当然作文最后还是有得分)。


分配任务


直接上对话详情,后端加上我一共3人


导师L:「任务我这边大概分配了下,你们先选吧」


我内心很慌,我一个都看不明白要怎么做


不知所措的我:「要不我拿剩下的」


同事P:「那把这个、这个、这个给我吧,剩下的你们分?」


导师L看着我:「那就这样分,你做那个、那个、那个,有问题随时找我」


不知所措的我:「好的,我主要是不熟悉这块业务,有问题我先整理出来再一起问下你呗」


这里有个关键点,整理完问题再一起咨询,切记遇到一个问一个
态度摆正,表现得自信点,第一次在同事面前“刷脸”,印象要留好一些

研发阶段


我的任务主要是客户群统计模块


导师给我开了两个服务的权限,让我先看看代码


懵逼的我:「L哥,要不大概说下在那部分写的统计数据?我应该从哪些表出结果?」


导师L:「你先看代码,里面都有逻辑,你看得懂」


无语的我:「好的」 内心(这么玩儿是吧)


知道那代码有多难懂吗?全都是A队列推到B队列,判断后再推C队列,并且还有了很多观察者模式。可能有兄弟姐妹问:「看不懂注释?」。注释少得可怜,也就一些字段含义,不过看单词也能看出来。


队列和队列之间很难看懂,并且很多跨服务的队列,给我开的两个服务根本不够,前后一共加上4个服务才把统计的逻辑串起来,我还专门画了个流程图出来


不管代码设计和质量如何,作为新人别公开喷前辈的代码
前期不要加入太多个性化的代码和设计,每个公司的要求不一致,最好的方式还是模仿
逻辑复杂的话,建议画一个流程图or时序图,架构图的话还是问下老同事,自己画可能不准确
不要轻易下手编码,确保自己很明确整体逻辑了再跟熟悉的同事复述一遍先

好吧,我终于找到逻辑线了(花了1天半时间,留给我开发的时间很近很近),但我发现,结果表很多很多,有AAA_statistics、BBB_statistics、CCC_statistics...... 我拿不定主意,刚好我也对这几个服务熟悉得差不多了,于是我拿着这些成果去问导师L


诚恳的我:「L哥,帮忙看看这几张表,我感觉有一些数据是重复的,还对不上数,帮忙看看呢?」


导师L:「逻辑都捋清楚了吗?」


我直接掏出了我的流程图


导师L:「这是JW(我们组的TL)给你的吗?」


求知的我:「我自己画的,不晓得准确性怎么样,帮忙check下呢」


导师L:「主要是我这还有点事,你再看看吧,晚点我们过一下」


前期难免会有很多问题,但自己也要有点准备,否则被问成麻瓜,印象分直接拉低
不知道的不要说"不知道",可以说"我还不太熟悉,我先去看看逻辑,X哥要不跟我说下大概位置或则有啥文档?"

到了晚上7:00左右,我发现L哥不见了,后来才晓得那天他溜得挺早的。只剩我原地爆炸,明天要联调了,我关键的数据组装service还只有一行//TODO。没招了,我按照我的想法和数据指标,找了几张最合适的表,把数据产出了。


第二天


我早早地来公司,重新check了下代码并又调试了几次,除了数据对不上没啥其他问题。导师L带着早饭来到公司,我还等到吃完早饭再去问了下。


疲惫的我:「L哥,你看我用这张统计表去输出功能有问题没?」


导师L:「就那么几张表,你造几条数据不就看出来了」


疲惫的我:「我造了几条数据,但是昨天的数据我看今天才过来,昨天忘了记录过程」


导师L:「怎么可能,你怎么造的数据,算了等会儿我看一下」


......


过程就不细讲了,总之,不好受...... 最后问题也定位到了,是导师L当初做测试,把定时任务往后延了1天。好吧,这还有定时任务的事儿?我只能看代码看到一堆数据同步的接口,真的是应征了那句话:【最怕的是:我不知道我'不知道'】。


时间允许的话,着手开工前还是留一份概要设计的存档,别把坑都留给后面的人了
流程图、时序图、架构图等,前期多花时间,少走弯路
心态摆好,我们是来打工挣钱的,交不交朋友是其次而已,关系不恶化怎么着都行

而后,比较顺利地进行到提测阶段,bug真的是多得要命,主要是以下几点:


1、数据权限没加(就是prd文档上写的跟xxx模块保持一致逻辑)


2、数据同步时好时坏,排查后发现是定时任务不稳定,大家都在一个环境提测版本,都在修改功能


3、未做改造的功能点测出历史bug(功能类似,故测试同学也纳入了测试范围)


4、服务被其他版本覆盖


导致最终版本交付时,我个人产生了大概20+个bug。周五下午TL专门找我谈话,约谈此事,大概意思是版本复杂度不高,但bug数过多,对我的版本质量不满意。对此,我也阐述了我的解释,这里我就不细说解释的话,大概从以下几点去阐述


不要丢锅,先把由自己粗心产生的bug讲一下,记得提一下数据,因自身代码质量产生了X个bug,后续会加强编码质量,多自测
也不要背锅,说下由于环境问题导致了X个bug的产生,并给出自己的建议,是否能做环境隔离,一个环境只能容纳服务不冲突的1~2个版本
注意下,TL直接对话的机会并不是很多,可以结合自身入职以来的经历,提一些建议(不用管是否重要)
总之,事事多总结,否则像这种情况下TL突然找咱们约谈,说不出个123,印象分会很差

项目总结


在项目研发中,不一定能得到公司前辈们的"关照",这时候就需要先自己憋一下(注意合理安排时间),怎么着也能憋出点内容,那这这些内容再去咨询,效果会好很多。像我这种被孤立的情况,我也不好说是不是常态,我个人还是认为好同事还是居多的。总之还是与同事搞好关系,或者关系一般遇事能帮忙也行,不要跟任何同事把关系闹僵(哪怕脾气差、技术菜、背后勾心斗角)。


还是那句话,遇事不要慌,先调整好心态(道理都看得懂,但希望大家都能做得到),尽力吃透项目再开始施工,否则返工或者低质量产出不好避免。


多做总结,不甩锅不背锅,不管是项目总结还是转正答辩还是晋升答辩,都能有个有条理有依据的总结出来。这点在职场中至关重要。


作者:snowlover
来源:juejin.cn/post/7347542133610364980
收起阅读 »

低谷期可能是在救你

怎么来定义低谷期? 我觉得真正的低谷期是迷茫,挫败,痛苦,自我怀疑等等,反正一定是比肉体上的痛苦更煎熬! 可能你会觉得暂时性找不到工作,面试受挫,分手等是你的低谷期,实则不然,这大概是一个不敢面对自己的借口。 因为多数人找到工作后,只要能在温饱线上,那么90%...
继续阅读 »

怎么来定义低谷期?


我觉得真正的低谷期是迷茫,挫败,痛苦,自我怀疑等等,反正一定是比肉体上的痛苦更煎熬!


可能你会觉得暂时性找不到工作,面试受挫,分手等是你的低谷期,实则不然,这大概是一个不敢面对自己的借口。


因为多数人找到工作后,只要能在温饱线上,那么90%的人就会心安理得摆烂,和男女朋友复合后,依然是维持原样,不会被爱情去刺激自己成长。


如果用工作和分手这两件事情来描述真正的低谷期,那么我觉得应该是这样描述的:


自己付出了很多,每天都像一条疯狗干,工作和学习的时长维持在18个小时左右,坚持了很久,但是没有收获自己想要的东西,希望还是如此渺茫,于是产生严重的自我怀疑,挫败,深圳绝望!


自己一直在努力,在慢慢成长,目标越来越近,但是自己爱得死去活来的女朋友实在等不了自己成长,自己变强,所以无情的选择离开。


经过上面的描述,成为了毋庸置疑的低谷期。


因为没经过描述之前其实你是没有任何斗志的,目的就是能安心混日子,可以用摆烂来形容,和女朋友在一起,自己也不需要啥成本,她也没有啥诉求,所以算得上是互相将就。


但是经过描述后,实际上你的努力近乎疯狂,对于成功是无比的渴望,但是迟迟没降临到你的身上,而女朋友是在你身上压了筹码的,而你又非常爱她,但是迟迟不能让她压的筹码赚个翻倍,所以离开成了定局。


这下就一目了然了吧。


所以这时候你再去回想一下自己所谓的低谷期,是否真的是低谷期?还是自己矫情?


从上面的场景我们能看到深刻二字,第一个是根本谈不上深刻,而第二个是无比的深刻,如果你经历过,那么你自然能理解!


只有让自己刻骨铭心和痛苦的事情才能让自己成长,其他的基本不能。


就像你比较肥胖,三高找上你,家里人叫你不要再吃垃圾食品,不要喝饮料,但是这时候你还没真正躺在病床上,你基本上不会去听。


但是如果此刻你躺在病床上,插着呼吸管,医生给你说,如果你再不注意饮食,那么你很快就会死掉。你看你还会不会再去吃垃圾食品,喝饮料。


所以说,只有让自己脱一层皮,自己才会意识到问题的所在。


那么低谷期里,也自然会脱一层皮,甚至还会换骨头,那么你觉得这难道不是最佳的成长期吗?


所以一个人能遇上真正的低谷期,其实是一种幸运,应该要感谢这个遭遇。


就像一个朋友,因为一些原因导致自己不能再继续读书,家里为了自己的事情而负债累累,自己承受巨大的压力,想死的心都有了。


但是在这段堪称被恶魔惩罚的时期,他没有一蹶不振,反而置之死地而后生,最后无论是财富还是个人能力,阅历都有很大的提升!


后面和他聊天的时候,他说那是自己最痛苦,最无助的时候,但是自己庆幸没有放弃,才造就了一身钢筋铁骨?


所以你说这个低谷期是不幸的吗?


不是,这算的上是恩赐,因为并不是谁都有这种机会。


所以我们在低谷期的时候,如果能有把它作为翻盘的机会的思想,那么它一定是很难得的机会!


但是如果把它作为上天对自己的惩罚,从而一蹶不振,那么其实是错失一次很好的机会,并且也学让自己越陷越深!


作者:苏格拉的底牌
来源:juejin.cn/post/7349750846900125748
收起阅读 »

探索个人IP&副业第三个月的思考:未经审视的人生不值得过

前言 Hi 你好,我是东东拿铁,一个正在探索个人IP&副业的后端程序员。 个人IP探索的第三个月,不再是一往无前的埋头苦干,一腔热血之余,对自己的能力探索与兴趣挖掘,成为了日常生活的主线。 为了更好的坚持下去,希望自己能够找到自己最擅长、做起来最愉悦、...
继续阅读 »

前言


Hi 你好,我是东东拿铁,一个正在探索个人IP&副业的后端程序员。


个人IP探索的第三个月,不再是一往无前的埋头苦干,一腔热血之余,对自己的能力探索与兴趣挖掘,成为了日常生活的主线。


为了更好的坚持下去,希望自己能够找到自己最擅长、做起来最愉悦、自身价值观又认可的事情。但最近一段时间,我意识到,我其实并不了解我自己。想认识自己,也不是一件简单的事情。



古希腊哲学家苏格拉底曾说:“未经审视的人生不值得过。“



话不多说,看看最近一段时间,我身边发生的事情与思考吧。


经历AI的诱惑,坚定内心的方向


其实在23年年底刚开始写作的时候,自己就对自己列了几个方向


其中,AI一直是我自己认为一个很重要的方向,时代大趋势下,所有行业只要加上AI,似乎都变得有些不一样。


image.png


24年年初,我第一次试着去了解AI的工具,是因为那时看到一个圈友,做了一个AI艺术二维码。于是我也下载下了stable-diffusion,准备大展身手一把。


本来是这样想的,发个朋友圈,如果有想要做艺术二维码的,我5块钱给他生成一个,怎么着也算开启了副业收入对吧。


结果人家做出来的是这样的,蛮好看。


image.png


我生成出来的,丑就不说了,问题是扫都扫不出来,就很搞笑。


苦于周边暂时没有大佬支持,也有着别的事情需要做,就暂时被我搁置了。


我的内心其实对AI感兴趣,但实际上,还是以一个程序员思维来考虑的。举一个例子,就想现在.NET的就业环境已经逐渐减少,如果我毕业时选择了一份.NET的工作,那么市场需求一定是很小的。


所以我才会对AI感兴趣,我的思路还是,或许5年后,Java已经不行了,但是算法开发、模型开发可能成为市场需求主流,为了找到工作,不得不去学习AI相关。


这件事情埋在我心里,虽没干成,但毕竟没有搞出来,心里还是有点不甘心的。


从过年伊始,就通过各种渠道,了解到了AI破局社群,即将迎来拉新。那时候我了解到,原来搞AI类应用,其实是有一个专门的社群的,里面也有各种各样的项目让你去落地,还有专业的人给你指导,我之前没跑出来的AI二维码,只要加入,遇到的问题肯定就能解决。


面对着铺天盖地的宣传,自己内心也逐渐有些动摇,一边是追求热点,迅速满足。一边是继续学习写作,延迟满足,看着许多圈友入局,内心还是挺焦虑的。


最终还是克服了自己短期尝试AI的想法,两个原因:



  1. 自己在尝试副业的伊始,就决定2024上半年,我不会思考变现问题,主业还能养活自己。

  2. 既然决定先好好锻炼写作能力,那就应该持续内化基本功,不追求短期目标。


人的精力有限,需要放在有用的地方。


关于写作


上了热榜,占据首页


经过一周时间的打磨,之前经历的一篇文章,竟然上了热榜第一,6000多字的碎碎念能被大家看到,不少朋友给我说能够感同深受,一切的努力都值得了。


image.png


被更多的人看到,固然是好事,但在写这篇文章的过程中,也发现了不少问题,其中低效、内耗的问题,最为严重。


首先,6000多字的文章,完全是个人经历与思考,纯手写的话,如何组织语言,安排好顺序,就是一个最大的问题。


其次,如何把结构梳理好,能够更有连贯性,才能让大家在看的过程中,不枯燥乏味,我花费了非常多的时间。


最后,因为事情涉及到不少真实经历,受限于篇幅,不能完全的呈现给大家,如何选择最能让大家共鸣,最能给大家带来价值的地方,也蛮头疼的。


与现在利用AI工具,一天能够四五篇文章的作者比起来,效率简直低的可怕,虽然带来的价值不一样,但是流量就是这么多,想让更多人看到,效率如何提高,是我接下来要重点思考的事情。


关于输出的“困扰”


经过3个月的输出,我不出意外的遇到了“缺少话题”的情况,这也是最近更新频率变低的最主要的原因。


在这段时间,虽然输出频率降低,但话题的收集没有落下,每当有一些小点子,我就会先记录下来,每天翻一翻,去看看哪些是最想写的。


但实际上,即使收集了很多素材,如果你没有太多想说的话,无疑也只是罗列旧知识,没有新观点,我只想说点新颖的,所以迟迟没有动笔。


为了解决这个问题,两个方法和大家分享下


先立后破


先立后破,虽然话题素材减少,但强制要求自己,每周都要有所输出。


为了达成这个任务,我被迫搜集很多素材,先丰富自己的素材库,然后选择自己最有表达欲的主题,详细去写。


为什么要先立后破


任何事情都有一个逻辑,就是先别管技巧或者合理性,也别管效果如何,先给它规定一个数量,把数量做到了,慢慢的,你就会因为数量而倒逼自己去琢磨如何研究质量。


写作这件事也一样,即使我不知道写什么,也要强迫自己动笔去写,自己在输出这件事上,依然坚信着一句话。



数量不一定能决定质量,但一定能决定重量。



定扩联思维


先确定


能输出的点有很多,技术、副业、写作、复盘,先把内容方向定下来,比如我今天选择的方向就是复盘。


后扩展


扩展的话就好说了,既然是复盘,每一件事情都可以展开来讲,AI的一些经历。关于输出的困扰,输出一些方法论。


再联想


根据自己阅读、学习过的内容,进行发散。比如我深入思考的个人定位问题,最近的所学所想,都可以随着复盘输出出来。


个人定位


这个月花费最多的时间,就是在思考如何有一个清晰的定位。思考过程中问自己的几个问题,也在此罗列出来,如果你也想找到个人定位,也不妨对着这几个问题问一下自己。


职业与专业知识


7年后端研发工程师,北漂回二线城市的大厂程序员。毕业半年裸辞北漂,但经过几年北漂后,为了追求内心、照顾家庭,6年后回到二线城市发展。


北漂阶段,从30人小公司,最终进入大厂。大厂期间面试人数50+,对于求职面试、职业规划有着不少宝贵经验。


完成北漂回归二线城市,完成了城市选择,公司判断,薪资谈判,心里建设等一系列流程,各种有些许挫折,但都一一完成拆解。


善于在复杂项目中抽丝剥茧,但缺乏创造力。经手的项目无论难度多大,都可以极快的完成梳理与上手。但每当新业务开展,思路总会比较局限。


喜欢的博主


个人非常喜欢的博主是,半佛仙人,18年从公众号关注至今,文章几乎一篇不落。


image.png


为什么喜欢?我简单的想了下,有一下几个原因。



  1. 有一定的专业性,瑞幸等一些文章,业内出名,如果大家听说过半佛,大概也看过那些非常出名的文章。

  2. 够肝。热点时事跟踪及时,比较重要的热点新闻,时事动向,他一定参与进来。虽然从作者的角度来说,肯定是要跟着热点和流量走,但对于我这种几乎不看微博和新闻的人来说,能让我省下很多无效时间,还能了解到很多最新的新闻。

  3. 够骚,从他的ID就看出来了:banfoSB,他的文风是我关注的所有博主里,最有特点的。


以上,羡慕。在我眼中,能毫无顾及的表达出自己的看法,让这么多人看到,对于一个爱写东西的人来讲,无疑是一件幸福的事情了。如果这件事情还能赚到钱,那更是锦上添花。


业余爱好


大学业余时间除了打游戏,就是谈恋爱,一上高数就睡觉,下课铃响就起床,


直到看了一本书《皮囊》之后,开始热爱上了阅读。虽然自己生在城市,完全没有农村经历,但对《皮囊》《活着》《兄弟》等很多农村作品,阅读的时候却有着特别大的感触,文中主人工经历越苦难,我的感受越心酸。


后来发现,老读这种文章,人都快看emo了(许多穷苦的事情,自己又没有能力改变什么)。


后来大学期间看了《嫌疑人x的现身》(短篇小说,非常精彩),了解了东野圭吾,对悬疑类作品有了极大兴趣,花了半年的时间就把他大多数重要的作品都看了一遍。印象最深的是《白夜行》,从第一次打开《白夜行》到最终看完,几乎过去了半年的时间,但是《嫌疑人x的现身》只需花了2天时间我就看完了。


但最终读完《白夜行》后,其中的精彩程度让我认为这是东野圭吾小说系列在我心中的No.1。这本书也让我意识到长篇小说的精彩之处,前面之前认为的枯燥的铺垫,到最后都是拍手称绝的伏笔。让我对延时满足这四个字,有个更深的体会。


image.png


后来又听说了村上春树,《挪威的森林》目前为止读了四遍,闲下来仍然会打开翻一翻。里面一些句子,一直在潜移默化的影响着我



不要同情自己,同情自己是卑劣懦夫干的勾当。


所谓绅士,就是做自己该做之事,而不是想做之事。



擅长的事情


我的盖洛普第二名和第五名,是和谐和体谅,遇见冲突解决冲突,并能够设身处地的体会他人的感受。所以之前有很多朋友和我说过,和我聊天,即使问题解决不了,心理上也能舒服很多。


image.png


或许你想找对象,我能帮你发现一些你潜在的问题,帮你去想应该怎么做,才能得到妹妹。


或许你面临裁员、换工作,我能根据你现有的能力与过往的经验,帮你规划提升方向。


或许你面临职场困惑,我也可以根据过往经验给出一些意见。


如果你有类似的问题,也欢迎你来找我聊聊。


说在最后


这次的复盘就先聊到这里了,有小的高光时刻,也有阻碍和自己的思考,感谢你能看到这里。




作者:东东拿铁
来源:juejin.cn/post/7349856694996074550
收起阅读 »

宏观经济的一些判断

估计谁都没想到2023年,疫情恢复的第一年竟然如此:大厂裁员、楼市继续下跌、年底股市暴跌等。 这篇文章说下笔者对宏观经济的一些理解和判断,以试图解释过去一年发生的一些事情。 宏观经济周期 笔者看来,由于美元具备全球货币属性,美元加息是全球的麻烦。所以总体而言,...
继续阅读 »

估计谁都没想到2023年,疫情恢复的第一年竟然如此:大厂裁员、楼市继续下跌、年底股市暴跌等。


这篇文章说下笔者对宏观经济的一些理解和判断,以试图解释过去一年发生的一些事情。


宏观经济周期


笔者看来,由于美元具备全球货币属性,美元加息是全球的麻烦。所以总体而言,全球经济处于美元加息影响下的结果中,也就是处于美元回流,全球货币紧缩,全球经济处于下行周期中


但每个主要经济体又有其自身的宏观经济周期,比如说我们国家,疫情三年为了人民的生命健康,我们国家没有像西方打开方便之门,大肆放水,而是选择严守死防。


三年疫情,我们国家保护了人民的生命健康,但我们也封闭了三年,紧缩了三年。我们国家处于疫情恢复周期中,处于上行周期中。但始作俑者的美国因为超发货币,自身经济过热,所以需要降低过热经济,所以宏观经济也处于下行周期中。


这里说一个题外话,宏观经济是通缩好还是通货膨胀好呢?实际上,过分的通缩和过分的通货膨胀都不好,适度的通胀最好,一般来说维持在2%左右是比较好的,这也就是美国一直想通过加息实现的通胀水平。


不管是通缩还是通胀代表的都是一种趋势,通缩经济逐渐下行,规模逐渐减小,反之通胀经济处于上行,规模逐渐扩大,这样才能实现GDP的增长,实现经济的发展。


回来继续说宏观经济周期,当下国家要做的就是让经济处于扩张区间,或者说实现经济的适度通胀。


2023年CPI和PPI一直不温不火,其实有一点通缩的迹象,所以国家在出台各种手段改善这种迹象:



  1. 对楼市逐渐降低首付比例,逐渐放开楼市,逐渐降息,逐渐降低存款准备金等

  2. 对股市降低印花税,转融通暂停,加大逆回购力度,证监会新管理层上任等


但改变趋势谈何容易,同时还要考虑美国的加息节奏。所以出台的手段并不是那么尽如人意,也因为受到美国加息节奏的影响,为了维持外汇的稳定性,出台的时机也并未尽如人意。


笔者觉得正因为上述原因:美元加息周期、国内降息周期导致2023大厂裁员、楼市继续下跌、年底股市暴跌。


2024年宏观经济


目前美国已经暂停加息半年,加息周期已经到顶,预期5、6月份后降息。也正因为暂停加息,加息到顶我国央行今天进一步降低5年期贷款利率。


2024年的国内的宏观经济依然是将经济恢复为适度通胀的水平。笔者的判断是在汇率稳定的前提下,稳定楼市,因为楼市涉及的面太大。稳定了楼市才能稳定经济稳定预期,才能稳定股市。


完全有可能的是央行在美国降息后选择再一次降息贷款利息的方式,加强人们的信心,加强人们对国家进一步搞活经济的决心,给人们信心。


稳定楼市而不是大力发展楼市。笔者认为未来国家的发展会逐渐向高科技产业倾斜,从依靠楼市带动GDP增长改为依靠科技带动。


综上,一些配套的改革一定也会有:比如真正支持优秀公司发展的证券市场,比如政府职能转变为服务好企业,比如更加开放的区域市场(现在的浦东新区)等等。


而笔者比较关心的股票市场,隶属于证券市场,笔者觉得未来中国的股市一定会越来越好,尤其优秀的科技公司。


(本文完)


作者:通往自由之路
来源:juejin.cn/post/7337227407365963803
收起阅读 »

打工人应避免被过度体制化

《肖申克的救赎》是一部令人震撼的电影。其给我留下深刻印象的不止男主的筹谋,还有终获假释,却选择上吊自杀的老布。老布是一个悲剧人物。 老布被关押监狱五十年。半个多世纪,老布从青年变为白发苍苍的老头,他最终熟悉了监狱的一切,适应了监狱的一切,也和监狱捆绑在了一起。...
继续阅读 »

《肖申克的救赎》是一部令人震撼的电影。其给我留下深刻印象的不止男主的筹谋,还有终获假释,却选择上吊自杀的老布。老布是一个悲剧人物。


老布被关押监狱五十年。半个多世纪,老布从青年变为白发苍苍的老头,他最终熟悉了监狱的一切,适应了监狱的一切,也和监狱捆绑在了一起。用电影中的话来说,老布被监狱“体制化”了,包括他的自我认同,自我习惯。他依赖这个监狱。


也正因为此,出狱后的老布因为无法适应、融入发生巨变的社会环境,选择结束自己的一生。


体制化是指是个人或群体在某种环境中逐渐适应并接受其中的规则、习惯、意识和氛围,以至于这些成为其思考和行为的一部分。比如说销售人员更会自我激励,司机师傅更容易记下位置路线,财务人员更细致……


现代社会高度发展,每个人都不可避免的依赖某个组织或企业。为了融入组织或企业,被体制化是必然。但过度被体制化,比如长期生活在农村的老人,长期在高速口收费的收费员,长期无法晋升的公司老白兔……不利于人的发展,应该主动避免。


分工


现代企业建立的基础之一是大规模生产下的分工,分工可以提高生产效率,但分工也让人失去独立性。就拿上面长期在高速口收费的收费员举例,几年前河北高速一个收费员被辞退,就闹了起来,原因是他别的什么都不会了。


长期单一职责一旦被离职很容易陷入困境,轻者生活质量下降;重者长期失业;更重者,如老布一般选择终结自己的生命,事实上前几年就发生了这种事……


企业机会狼多肉少


几年前读过一句话:我们的社会实际是一个精英筛选系统,大多数人存在的意义是辅助筛选。这句话套用在企业也适用,企业是一个小型的精英筛选系统。


这些年互联网行业流行的所谓35岁职场危机,背后实际是部分企业认定35岁没能成为精英,也就不具人力性价比,选择不再对其招聘。


35岁大部分都有了家庭,要是35岁没有成为精英,相关企业招聘的意愿又不强,只能等着被辞退。要是在被过度体制化,被拴在一家企业,那无疑是雪上加霜。


体制化是放弃整个森林


我对企业有很多定义,其中之一企业是社会当中满足一系列特定需求的组织。一系列特定需求实际是局部市场。在局部市场里,企业注定机会有限。而市场本身比企业拥有更多机会,被过度体制化会被动放弃拥有更多机会的可能。


积极培养第二曲线甚至第三曲线


随着技术的提高,经济的发展,现代职业的生命周期在缩短。我认为每个人应该积极培养第二甚至第三职业。第二职业可以是自媒体,比如写作、比如up主、再比如小红书博主……可以是其他擅长的,可以利用下班时间去做的事业。


第三职业可以是投资人,投资是坐顺风车的学问,重要的是识别顺风车。做投资可以先从二级市场,也就是股票市场开始(投资需谨慎)。要能够借国家发展的大势,享受国家发展带来的红利。


我之前写过一篇关于宏观经济的文章《宏观经济的一些判断》。目前,我国经济处于上行周期中,受房地产拖累,经济爬坡有些缓慢。上个月CPI同比上涨0.7%,消费意愿在加强;上个月社融处于增长态势,经济活动相对活跃,上个月规模以上企业工业增加值显著增长……


种种迹象表明经济在好转,我也相信经济一定会好起来,经济好起来叠加国家对证券市场的进一步规范,不久以后股市完全有可能成为新的国民财富蓄水池。


结尾


总之,在工作过程中要识别哪些规则、习惯、意识和氛围,长期来讲是真正的机会,哪些不是。到了一定年龄,看不到成为公司精英的希望,应发展更多社会生存技能,在社会这个更大市场中生根发芽,创造财富,获取财富。


也希望能够直接借到国家发展大势,直接享受国家发展红利。


作者:通往自由之路pro
来源:juejin.cn/post/7348013957732941876
收起阅读 »

💀填好个税,一年多给几千块 ~ 聊聊个人所得税,你该退税还是补税?写一个个税的计算器(退税、补税、个税)

前言 一年一度个税年度综合汇算清缴的时间又到了,作为开发者的你,肯定过了起征点了吧。🫤 去年退税退了 5676 ,今年看这个估计得补好几千,但是个税年度汇算清缴还没有预约到,抓紧提前算算金额,做做心理建设。\同时,了解个税都扣在哪了,才可以让我们合理避税~ 下...
继续阅读 »

前言


一年一度个税年度综合汇算清缴的时间又到了,作为开发者的你,肯定过了起征点了吧。🫤


去年退税退了 5676 ,今年看这个估计得补好几千,但是个税年度汇算清缴还没有预约到,抓紧提前算算金额,做做心理建设。\同时,了解个税都扣在哪了,才可以让我们合理避税~


下面我们简单聊聊 补税预缴 ,顺便讲讲专项附加扣除应该怎么填。


以及带大家写一个个税计算器。你可以通过码上掘金查看 在线 svelte(无UI) 版 ,后续也会推出其他框架版。


为什么你需要补税?


大多数情况下,公司发工资会替你把税交了,这个行为叫预缴。


为什么预缴呢?因为国家规定:



《个人所得税扣缴申报管理办法(试行)》(国家税务总局公告2018年第61号发布)

第六条:扣缴义务人向居民个人支付工资、薪金所得时,应当按照累计预扣法计算预扣税款,并按月办理扣缴申报。



这也就是我们每个月发工资都会扣税的原因。


那为什么需要补税呢?因为预缴是根据你在当前公司的收入进行缴税,公司会计算你的累进税率,你会发现每到年底税交的越来越高了,这是累进预缴导致的。


有些人在年中换了工作了,新公司不知道你之前已经交到哪个阶段的个税了,因此预缴时计税金额会重新累计。


因此补税的原因不外乎:



  • 工作变更

  • 公司主体变更(如:公司拆分)


为什么说预缴是天才发明?


预缴制简直是个天才发明,不但会大大减少逃税人数,而且能减轻税务工作量(转移至各公司),且可以让缴税的人对税率的感知没有那么强烈。


达成这种效果主要原因有两点,分别是 损失厌恶心理账户


损失厌恶


人们对损失的敏感程度通常远远大于对同等价值的收益的敏感程度

人们对损失的敏感程度通常远远大于对同等价值的收益的敏感程度

人们对损失的敏感程度通常远远大于对同等价值的收益的敏感程度


牢记这句话。


一个最简单的例子,短视频中经常会出现的 最有效的 6 条学习方式,最后一条最重要 。这种放大损失的语言,常常能诱发更高的完播率。



虽然我很讨厌以这种方式留住用户,但常常在刷到这类视频时,也忍不住多看一样,虽然知道它最终可能也没什么实质内容。



还有一种就是我们常常刷掉一个视频,又返回去看一眼,又刷掉又返回去。我常常会有这种心理,这个视频我是不是应该看一看的纠结。


个税也是同理,个税预缴是减少我们的收益,而个税年终汇算则是直接让我们从口袋中掏钱。


就算汇算综合到月度计算,同样也是,一种是公司扣完发给你,另一种是发给你之后你再掏出来一部分。大家感受一下这其中的区别。


心理账户


人们可能会将个税缴纳视作开销,而且是意外开销,意外开销总是让人痛苦的。


比如我每个月 1w 块,其中 3k 拿来租房,3k 拿来吃饭, 2k 拿来娱乐,2k 拿来缴五险一金。


这时候到年终汇算时,人们则容易苦不堪言。


且这种带来的直接后果是,我想把税留到最后一天交,同时最后一天也很容易忘记交,因为大脑也不想要这种意外支出。


最终则导致 漏交、拒交 个税的人数大大增加。


专项附加扣除严谨度



  • 子女教育(未婚,无接触)

  • 赡养老人(容易被查)

  • 继续教育 - 学历提升(基本不查)

    • 学历提升可以选择一个对应学历,每个学历 4 年,共 16 年左右抵税



  • 继续教育 - 证书获取(基本不查)

    • 证书获取有人一个证书可以一直抵税,建议: 营养师证、焊工证等



  • 租房买房(基本不查)

  • 大病医疗(未填过,未知)


开发


首先咱们先写个个税计算器的 class ,个人所得税英文简称 IIT (Individual Income Tas)


class IITCalulator {}

添加需要计算的内容


众所周知,

个税计算法:应缴税款 * 对应税率 - 速算扣除

应缴税款计算法:工资 - 五险一金缴纳额 - 专项附加扣除


因此我们先添加 工资 、 五险一金 、 专项附加扣除 的属性。


工资


我们工资有两个组成部分,分别是 固定工资 和 年终奖(如果有的话)。


class IITCalulator {
private salary: {
monthlySalary: number;
yearEnd: number;
} = {
monthlySalary: 0,
yearEnd: 0,
};

/**
* @description 添加工资(通过工资计算年薪)
*/

addSalary(
monthlySalary,
yearEnd?: { value: number; type: "month" | "amount" }
) {
this.salary.monthlySalary = monthlySalary;
if (yearEnd) {
this.salary.yearEnd =
yearEnd.type === "amount"
? yearEnd.value
: monthlySalary * yearEnd.value;
}
}
}

五险一金


这里直接给了固定金额,可以通过查看每月扣除得知。



考虑到有人不太清楚自己的五险一金缴纳基数,这里直接用了固定金额,后续可以扩展出通过缴纳比例自动计算



class IITCalulator {
private socialInsuranceMonthlyAmount = 0;

/**
* @description 添加五险一金,计算年五险一金缴纳额
* @param {number} monthlyAmount 月度缴纳金额
*/

addSocialInsurance(monthlyAmount) {
this.socialInsuranceMonthlyAmount = monthlyAmount;
}
}

专项附加扣除


专项附加扣除通过数组的方式存储扣除项。



  1. 子女教育

  2. 赡养老人

  3. 继续教育(学校)

  4. 继续教育(证书)

  5. 住房贷款

  6. 大病医疗


// 专项附加扣除类型
type SpecialDeductionType =
| "children"
| "elder"
| "education-school"
| "education-certificate"
| "housing"
| "medical";

class IITCalulator {
private specialDeductionTypes: Array<SpecialDeductionType> = [];
private medicalAmount = 0;

/**
* @description 添加专项附加扣除
* @param {string} type 专项附加扣除类型
*/

addSpecialDeduction(
SpecialDeductionType: SpecialDeductionType,
medicalAmount?: number
) {
this.specialDeductionTypes.some((t) => t !== SpecialDeductionType) &&
this.specialDeductionTypes.push(SpecialDeductionType);

if (medicalAmount) {
this.medicalAmount = medicalAmount;
}
}
}

计算 工资 、 五险一金 、 专项附加扣除


我们添加了基础属性,可以根据基础属性计算出对应金额。


工资


工资 = 月薪 * 12 + 年终奖


getYearSalary() {
return this.salary.monthlySalary * 12 + this.salary.yearEnd;
}

五险一金


五险一金 = 月缴纳额 * 12


getYearSocialInsurance() {
return this.socialInsuranceMonthlyAmount * 12;
}

专项附加扣除


专项附加扣除 = 扣除项的扣除金额合集



需要注意的是:大病扣除项是固定金额的



这里直接采用 reduce 进行累加。


/**
* @description 计算专项附加扣除
*/

private getSpecialDeduction() {
return this.specialDeductionTypes.reduce((r, v) => {
switch (v) {
case "children":
return r + 2000 * 12;
case "elder":
return r + 3000 * 12;
case "education-school":
return r + 400 * 12;
case "education-certificate":
return r + 3600;
case "housing":
return r + 1500 * 12;
case "medical":
return r + this.medicalAmount;
default:
return r;
}
}, 0);
}

计算纳税金额


我们基础数据都有了,就只差计算了。先通过基础数据计算应纳税所得额,再通过应纳税所得额计算个税。


计算应纳税所得额


calcIIT() {
// 计算年薪
const yearSalary = this.getYearSalary();
// 五险一金缴纳金额
const yearSocialInsurance = this.getYearSocialInsurance();
// 专项附加扣除金额
const specialDeduction = this.getSpecialDeduction();
// 计算需要缴纳个税的金额
let taxableAmount =
yearSalary - yearSocialInsurance - specialDeduction - 60000;
// 计算个税
return this.calcTaxableAmount(taxableAmount);
}

计算应缴个税


个税计算参考:


image.png


// 计算个税(金额 * 税率 - 速算扣除)
private calcTaxableAmount(taxableAmount: number) {
if (taxableAmount <= 36000) {
return taxableAmount * 0.03;
} else if (taxableAmount <= 144000) {
return taxableAmount * 0.1 - 2520;
} else if (taxableAmount <= 300000) {
return taxableAmount * 0.2 - 16920;
} else if (taxableAmount <= 420000) {
return taxableAmount * 0.25 - 31920;
} else if (taxableAmount <= 660000) {
return taxableAmount * 0.3 - 52920;
} else if (taxableAmount <= 960000) {
return taxableAmount * 0.35 - 85920;
} else {
return taxableAmount * 0.45 - 181920;
}
}

完整代码:


// 专项附加扣除类型
// 1. 子女教育
// 2. 赡养老人
// 3. 继续教育(学校)
// 4. 继续教育(证书)
// 5. 住房贷款
// 6. 大病医疗
type SpecialDeductionType =
| "children"
| "elder"
| "education-school"
| "education-certificate"
| "housing"
| "medical";

class IITCalculator {
private salary: {
monthlySalary: number;
yearEnd: number;
} = {
monthlySalary: 0,
yearEnd: 0,
};
private socialInsuranceMonthlyAmount = 0;

private specialDeductionTypes: Array<SpecialDeductionType> = [];
private medicalAmount = 0;

constructor() {}

/**
* @description 添加工资(通过工资计算年薪)
*/

addSalary(
monthlySalary,
yearEnd?: { value: number; type: "month" | "amount" }
) {
this.salary.monthlySalary = monthlySalary;
if (yearEnd) {
this.salary.yearEnd =
yearEnd.type === "amount"
? yearEnd.value
: monthlySalary * yearEnd.value;
}
}

getYearSalary() {
return this.salary.monthlySalary * 12 + this.salary.yearEnd;
}

/**
* @description 添加五险一金,计算年五险一金缴纳额
* @param {number} monthlyAmount 月度缴纳金额
*/

addSocialInsurance(monthlyAmount) {
this.socialInsuranceMonthlyAmount = monthlyAmount;
}

getYearSocialInsurance() {
return this.socialInsuranceMonthlyAmount * 12;
}

/**
* @description 添加专项附加扣除
* @param {string} type 专项附加扣除类型
*/

addSpecialDeduction(
SpecialDeductionType: SpecialDeductionType,
medicalAmount?: number
) {
this.specialDeductionTypes.some((t) => t !== SpecialDeductionType) &&
this.specialDeductionTypes.push(SpecialDeductionType);

if (medicalAmount) {
this.medicalAmount = medicalAmount;
}
}

/**
* @description 计算专项附加扣除
*/

private getSpecialDeduction() {
return this.specialDeductionTypes.reduce((r, v) => {
switch (v) {
case "children":
return r + 2000 * 12;
case "elder":
return r + 3000 * 12;
case "education-school":
return r + 400 * 12;
case "education-certificate":
return r + 3600;
case "housing":
return r + 1500 * 12;
case "medical":
return r + this.medicalAmount;
default:
return r;
}
}, 0);
}

calcIIT() {
// 计算年薪
const yearSalary = this.getYearSalary();
// 年终奖是否单独计税

// 五险一金缴纳金额
const yearSocialInsurance = this.getYearSocialInsurance();
// 专项附加扣除金额
const specialDeduction = this.getSpecialDeduction();
// 计算需要缴纳个税的金额
let taxableAmount =
yearSalary - yearSocialInsurance - specialDeduction - 60000;
// 计算个税
return this.calcTaxableAmount(taxableAmount);
}

// 计算个税(金额 * 税率 - 速算扣除)
private calcTaxableAmount(taxableAmount: number) {
if (taxableAmount <= 36000) {
return taxableAmount * 0.03;
} else if (taxableAmount <= 144000) {
return taxableAmount * 0.1 - 2520;
} else if (taxableAmount <= 300000) {
return taxableAmount * 0.2 - 16920;
} else if (taxableAmount <= 420000) {
return taxableAmount * 0.25 - 31920;
} else if (taxableAmount <= 660000) {
return taxableAmount * 0.3 - 52920;
} else if (taxableAmount <= 960000) {
return taxableAmount * 0.35 - 85920;
} else {
return taxableAmount * 0.45 - 181920;
}
}
}

最后


我最开始尝试写一个 UI 版。但后续感觉,UI 版对于不同语言的用户,会看起来很痛苦。

因此我通过纯 JS 实现,大家可以通过不同的 UI 调用该类,可以在各个框架中使用。

同时也通过 svelte 做了一个简略 UI 版,大家可以直接尝试。


最后,点赞、关注、收藏 ,祝大家多多退税~~


作者:sincenir
来源:juejin.cn/post/7342511044290789430
收起阅读 »

如果我贷款买一套 400W 的房子,我要给银行多送几辆迈巴赫?

买房攻略 2023 年至今,上海房价一跌再跌。俺已经蠢蠢欲动了,磨刀霍霍向"买房"。但是奈何手里钞票不够,只能向天再借 500 年打工赚钱。但是作为倔强的互联网打工人,想知道自己会被银行割多少韭菜。于是就写了个程序,用于计算我贷款买房需要多给银行还多少钱。这样...
继续阅读 »

买房攻略


2023 年至今,上海房价一跌再跌。俺已经蠢蠢欲动了,磨刀霍霍向"买房"。但是奈何手里钞票不够,只能向天再借 500 年打工赚钱。但是作为倔强的互联网打工人,想知道自己会被银行割多少韭菜。于是就写了个程序,用于计算我贷款买房需要多给银行还多少钱。这样我就能知道银行割我的韭菜,能省下几辆迈巴赫的钱了。


贷款利率



  • 公积金的贷款利率



    • 首房:贷款时间 <=5 年,利率为 2.6% ;贷款时间 >= 5 年,利率为 3.1%

    • 非首房:贷款时间 <=5 年,利率为 3.025% ;贷款时间 >= 5 年,利率为 3.575%




image.png



  • 商业险贷款利率



    • 贷款时间 <=5 年,利率为 3.45% ;贷款时间 >= 5 年,利率为 3.95%




image.png


代码实现



  • 以下代码,实现了:我贷款买房需要多给银行还多少钱


public class LoanAmountCalculation {

   //首套住房5年以内公积金贷款利率
   private static final double FIRST_HOUSE_ACCUMULATION_FUND_LOAN_RATE_WITHIN_FIVE_YEARS = 2.6;
   //首套住房5年以上公积金款利率
   private static final double FIRST_HOUSE_ACCUMULATION_FUND_LOAN_RATE_MORE_FIVE_YEARS = 3.1;
   //二房5年以内公积金贷款利率
   private static final double NOT_FIRST_HOUSE_ACCUMULATION_FUND_LOAN_RATE_WITHIN_FIVE_YEARS = 3.025;
   //二房5年以上公积金款利率
   private static final double NOT_FIRST_HOUSE_ACCUMULATION_FUND_LOAN_RATE_MORE_FIVE_YEARS = 3.575;
   //5年以内商业贷款利率
   private static final double COMMERCIAL_LOAN_RATE_WITHIN_FIVE_YEARS = 3.45;
   //5年以上商业贷款利率
   private static final double COMMERCIAL_LOAN_RATE_MORE_FIVE_YEARS = 3.95;

   public static void main(String[] args) {
       Scanner scanner = new Scanner(System.in);

       double houseAmount = getInputValue(scanner, "请输入预计买房金额(单位:W):", "请输出正确的买房金额(>0)!");
       double principal = getInputValue(scanner, "请输入您的本金(单位:W):", "请输出正确的买房金额(>0)!");
       if (principal >= houseAmount) {
           System.out.println("全款买房,崇拜大佬!");
           return;
      }

       double accumulationFundLoanAmount = getInputValue(scanner, "请输入公积金贷款金额(单位:W):", "请输出正确的公积金贷款金额(>0)!");

       double commercialLoanAmount = houseAmount - principal - accumulationFundLoanAmount;
       if(commercialLoanAmount <= 0){
           System.out.println("您的本金+公积金贷款已经够买房啦,恭喜大佬!");
           return;
      }else{
           System.out.println("您的本金+公积金贷款还不够买房哦,需要商业贷款金额为(单位:W):" + commercialLoanAmount + "\n");
      }

       int accumulationFundLoanYears = getInputIntValue(scanner, "请输入公积金贷款年份(单位:年):");
       int commercialLoanAmountYears = getInputIntValue(scanner, "请输入商业贷款年份(单位:年):");

       int isFirstHouse = getInputIntValue(scanner, "请输入是否首房(0:否,1:是):");

       LoanAmount loanAmount = calculateLoanAmount(
               accumulationFundLoanAmount, accumulationFundLoanYears,
               commercialLoanAmount, commercialLoanAmountYears, isFirstHouse);
       System.out.println("详细贷款信息如下:" + "\n" + loanAmount);
  }

   /**
    * 获取double类型的输入
    * @param scanner:Java输入类
    * @param prompt:提示信息
    * @param errorMessage:输入错误的提示信息
    * @return 一个double类型的输入
    */

   private static double getInputValue(Scanner scanner, String prompt, String errorMessage) {
       double value;
       while (true) {
           System.out.println(prompt);
           if (scanner.hasNextDouble()) {
               value = scanner.nextDouble();
               if (value > 0) {
                   break;
              } else {
                   System.out.println(errorMessage);
              }
          } else {
               scanner.next();
               System.out.println(errorMessage);
          }
      }
       return value;
  }

   /**
    * 获取int类型的输入
    * @param scanner:Java输入类
    * @param prompt:提示信息
    * @return 一个int类型的输入
    */

   private static int getInputIntValue(Scanner scanner, String prompt) {
       int value;
       while (true) {
           System.out.println(prompt);
           if (scanner.hasNextInt()) {
               value = scanner.nextInt();
               if (value > 0) {
                   break;
              } else {
                   System.out.println("请输入正确的年份(>0)!");
              }
          } else {
               scanner.next();
               System.out.println("请输入正确的年份(>0)!");
          }
      }
       return value;
  }

   /**
    * 功能:贷款金额计算
    * 入参:
    * 1.accumulationFundLoanAmount:公积金贷款金额 2.accumulationFundLoanYears:公积金贷款年份;
    * 3.commercialLoanAmount:商业贷款金额;       4.commercialLoanAmountYears:商业贷款年份
    * 5.isFirstHouse:是否首房
    */

   private static LoanAmount calculateLoanAmount(double accumulationFundLoanAmount, int accumulationFundLoanYears,
                                                          double commercialLoanAmount, int commercialLoanAmountYears, int isFirstHouse)
{
       LoanAmount loanAmount = new LoanAmount();
       //公积金贷款还款金额
       double accumulationFundRepaymentAmount;
       if(isFirstHouse == 1){
           accumulationFundRepaymentAmount = accumulationFundLoanYears <= 5 ?
                   accumulationFundLoanAmount * Math.pow((100 + FIRST_HOUSE_ACCUMULATION_FUND_LOAN_RATE_WITHIN_FIVE_YEARS) / 100, accumulationFundLoanYears)
                  : accumulationFundLoanAmount * Math.pow((100 + FIRST_HOUSE_ACCUMULATION_FUND_LOAN_RATE_MORE_FIVE_YEARS) / 100, accumulationFundLoanYears);
      }else{
           accumulationFundRepaymentAmount = accumulationFundLoanYears <= 5 ?
                   accumulationFundLoanAmount * Math.pow((100 + NOT_FIRST_HOUSE_ACCUMULATION_FUND_LOAN_RATE_WITHIN_FIVE_YEARS) / 100, accumulationFundLoanYears)
                  : accumulationFundLoanAmount * Math.pow((100 + NOT_FIRST_HOUSE_ACCUMULATION_FUND_LOAN_RATE_MORE_FIVE_YEARS) / 100, accumulationFundLoanYears);
      }
       loanAmount.setAccumulationFundRepaymentAmount(String.format("%.2f", accumulationFundRepaymentAmount));

       //公积金贷款每年还款金额
       loanAmount.setAccumulationFundAnnualRepaymentAmount(String.format("%.2f", accumulationFundRepaymentAmount / accumulationFundLoanYears));

       //商业贷款还款金额
       double commercialRepaymentAmount = commercialLoanAmountYears <= 5 ?
               commercialLoanAmount * Math.pow((100 + COMMERCIAL_LOAN_RATE_WITHIN_FIVE_YEARS) / 100, commercialLoanAmountYears)
              : commercialLoanAmount * Math.pow((100 + COMMERCIAL_LOAN_RATE_MORE_FIVE_YEARS) / 100, commercialLoanAmountYears);
       loanAmount.setCommercialRepaymentAmount(String.format("%.2f", commercialRepaymentAmount));

       //商业贷款每年还款金额
       loanAmount.setCommercialAnnualRepaymentAmount(String.format("%.2f", commercialRepaymentAmount / commercialLoanAmountYears));

       //公积金贷款超出金额
       loanAmount.setAccumulationFundLoanExceedAmount(String.format("%.2f", accumulationFundRepaymentAmount - accumulationFundLoanAmount));

       //商业贷款超出金额
       loanAmount.setCommercialLoanExceedAmount(String.format("%.2f", commercialRepaymentAmount - commercialLoanAmount));

       loanAmount.setTotalExceedLoanAmount(String.format("%.2f", accumulationFundRepaymentAmount - accumulationFundLoanAmount + commercialRepaymentAmount - commercialLoanAmount));
       return loanAmount;
  }
   @Data
   static class LoanAmount{
       /**
        * 公积金贷款还款金额
        */

       private String accumulationFundRepaymentAmount;
       /**
        * 公积金贷款每年还款金额
        */

       private String accumulationFundAnnualRepaymentAmount;
       /**
        * 商业贷款还款金额
        */

       private String commercialRepaymentAmount;
       /**
        * 商业贷款每年还款金额
        */

       private String commercialAnnualRepaymentAmount;
       /**
        * 公积金贷款超出金额 = 公积金贷款还款金额 - 公积金贷款金额
        */

       private String accumulationFundLoanExceedAmount;
       /**
        * 商业贷款超出金额 = 商业贷款还款金额 - 商业贷款金额
        */

       private String commercialLoanExceedAmount;

       /**
        * 总共贷款超出金额
        */

       private String totalExceedLoanAmount;

       @Override
       public String toString() {
           return "1.公积金贷款还款金额=" + accumulationFundRepaymentAmount + "万元\n" +
                   "2.商业贷款还款金额=" + commercialRepaymentAmount + "万元\n" +
                   "3.公积金贷款每年还款金额=" + accumulationFundAnnualRepaymentAmount + "万元\n" +
                   "4.商业贷款每年还款金额=" + commercialAnnualRepaymentAmount + "万元\n" +
                   "5.公积金贷款超出金额=" + accumulationFundLoanExceedAmount + "万元\n" +
                   "6.商业贷款超出金额=" + commercialLoanExceedAmount + "万元\n" +
                   "7.总共贷款超出金额=" + totalExceedLoanAmount + "万元\n";
      }
  }
}

代码输入,输出示例


6f9e90ab10c92d0a673777569a64f75.png


由上图可知,我要贷款买一套 400w 的房子,本金只有 120w,使用组合贷:公积金贷款 120w(10年),商业贷款 160w(20年)。最终我需要多还银行 230.07w,相当于买两辆迈巴赫的钱了,巨亏!


以上就是全部内容了,如果涉及到真实场景,还是需要根据具体的情况计算的!


作者:一只野生的八哥
来源:juejin.cn/post/7346385551366684722
收起阅读 »

用马斯克五步工作法重构支付宝商家账单

本文作者是蚂蚁集团数据研发工程师惠勒,将马斯克五步工作法应用在了实际项目中,实现了支付宝商家账单的重构,希望本文对想要降低系统复杂度的同学或者项目有所帮助。0. 概述支付宝中国数据团队在过去的一年里应用马斯克的五步工作法重构了有 10 年历史之久的支付宝商家账...
继续阅读 »

本文作者是蚂蚁集团数据研发工程师惠勒,将马斯克五步工作法应用在了实际项目中,实现了支付宝商家账单的重构,希望本文对想要降低系统复杂度的同学或者项目有所帮助。

0. 概述

支付宝中国数据团队在过去的一年里应用马斯克的五步工作法重构了有 10 年历史之久的支付宝商家账单,整体复杂度减少 60%,时效性提升 1 小时,计存成本降低 30%,理解和运维成本大幅下降。复杂度是很多问题的根源,既会增加运维的成本,又降低了支撑业务的效率。 账单重构的经验表明,相当大比例的复杂度是没有必要的,我们应该致力于把复杂的事情变简单,而不是倒过来做“防御性编程”。希望本文对想要降低系统复杂度的同学或者项目有所帮助。

1. 重构背景

1.1 什么是商家账单

商家通过支付宝发生业务,我们对他们提供相应的流水单或者凭证,这就是商家账单。商户可以到B站下载账单和他们自己的业务记录及资金变动期望逐一比对,确认所有业务和资金都按正确的期望的方式完成了处置,这个过程称为商家对账

支付宝目前提供了丰富账单类型,包括资金流水,交易订单,资产凭证,营销动账,费用账单以及一些列个性化定制账单。实现方式上则有在线实时账单以及基于 odps 的离线的日/月账单,其中在线账单主要用于业务查询,而离线账单则主要用于商家对账,本文所指商家账单主要指离线账单

图1:B站里的商家账单

1.2 为什么要重构

一句话概括:历时 10 年,积重难返

商家账单作为支付宝收单业务配套的基础产品,主要的服务对象是商家。和所有 To B 产品一样,其面临着“千人千面的个性化诉求和成本可控的快速支撑”的核心矛盾。在实现过程中,要么在原有逻辑上打个补丁,更多的时候是出于稳定性等因素考虑,不敢动原有的逻辑,于是就新起炉灶搞个新的字段。历时 10 年,资金流水账单搞出了上百个字段,很多字段的加工链路极其复杂。目前整个账单大概有几千个任务,近万的依赖关系,平均加工深度 20 多层,各种横向域之间的耦合,纵向层之间的调用层出不强,用一团乱麻来形容也不为过!

图 2:真实的账单血缘图

image.png

图 3:账单架构混乱的示意图

1.3 为什么是现在

主要是因为逻辑过于复杂,当前用于保障账单准确出账时效的成本已经过于高昂。

离线账单是拿去对账的,这就像有上百万商家拿着放大镜在找问题一样,不仅像金额,时间等字段不能有问题,各种订单号,门店 ID 等字段也偏差不得。而当前账单过于复杂,经常出现变更了这里漏了那里,或者是改了上游影响了好几层以外的下游。目前每年流转到二线研发同学的咨询就有几百例,一线外包和马力等同学接到的账单类问题更是以万计。

时效性方面的压力则有过之而无不及。由于需要对标竞对 T+1 10 点的出账时效,支付宝目前对客承诺 T+1 9 点出账,扣减掉在线账单文件生成和预留的异常处理时间,基本上要求离线账单需要 T+1 5 点 30 产出。作为蚂蚁唯二的两条最高级基线之一,运维同学承担了极大的压力,从 2023 年 9 月-12 月,运维同学在夜间共计响应 150+ 起电话告警,涉及天数 67 天,值班起夜比例为 67/122=54.9%。虽然引发起夜的因素有集群计算资源以及 odps 软件等外部因素,但根子上还是因为加工链路太长,给基线预留的余量不够。

为了彻底解决上述问题,我们决心重构支付宝商家账单,通过降低复杂度的方式,既提升用户体验又降低运维成本。

2. 重构目标

通过降低 50% 的复杂度,达到以下 5 点业务效果

  • 准确的

每个字段的含义是明确的,账单数据内部是一致的

  • 高时效的

    账单产出提前 1 小时
  • 好运维的

    重大问题能够快速一键重跑的(72h 降低到 12h 以内),日常的异常情况能够快速处理(1h以内),代码结构是好理解的(模块化的分层架构)
  • 易扩展的

    可扩展性强,对于各种业务需求的响应速度较快,不需要对代码逻辑大幅改动。有灰度环境的全链路回归链路,减少变更风险
  • 低成本的

    在保证回刷要求的前提下尽可能降低存储成本(降低 1/3 的存储成本),减少任务数量,降低计算成本(降低 1/3 的计算成本)

3. 应用五步工作法重构账单

马斯克在特斯拉和 spaceX 的成功经验告诉我们,应用五步工作法可以把复杂的事情变得简单,把高昂的成本打下来。所谓五步工作法,主要是

  1. 质疑,推敲需求,不要有愚蠢的需求;
  2. 删减,简化流程,精简部件或工艺流程;
  3. 优化,在前面两步的基础上做优化;
  4. 加速,在前三步的基础上加快迭代时间;
  5. 替换,在完成前四步之后做自动化替换。 商家账单的重构工作也或多或少借鉴了五步工作法。

3.1 质疑

第一步是质疑:为什么有那么多字段,为什么每个字段有那么多逻辑,为什么加工链路需要那么长。 带着这几个为什么,我们开始做字段梳理工作,核心工作是两项

  1. 梳理这些字段哪些是有人用的,哪些是没人用的。有人用的话有多少人在用,都是哪些商户
  2. 从末端表的字段出发,自下而上的梳理加工链路,穿透到最上游,看字段最终来源于哪些领域。

以最多商户使用的资金流水账单为例,上百个字段中仅有不到三分之一是核心字段,一半左右是个性化字段(使用商户数 100 以下),剩余大几十个都是无人使用字段;字段来源方面则集中在账务,交易,支付,计收费,结算,充转提等几个领域。从这些数字中我们得出以下两个观点

  1. 不需要那么多字段,可以先集中攻克核心字段
  2. 我们可以分域处理信息,再拼起来集中加工使用

3.2 删减

带着第一步质疑的观点,我们开始做删减,以核心字段为目标,落地如下架构设计 image.png

图4:重构的账单架构图

核心的工作有那么几项

  1. 把最终的一个对客账单字段,拆解为几个不同领域的字段加工。 如账单字段商户订单号,可以简化为如下规则:如果有交易号的话,则取交易号,否则使用账务域的外部流水号兜底。这样一来,一个账单字段就拆解为了一个交易域的字段和一个账务域的字段。对其余核心账单字段如法炮制,最终可以归到账务,交易,支付,计收费,结算,充转提等6-7个领域中去。
  2. 每个领域按照面向领域建模的方式进行中间层的构建,把需要的领域内的字段提前加工处理好
  3. 把(2)的结果拼接起来变成账单因子层宽表,再根据每个出账字段的加工规则,清洗出最后的账单字段
  4. 清洗出账规则,过滤(3)的结果,产出最终的日明细账单。日汇总,月账单等都基于日明细账单加工。

    特别需要注意的是,在这个阶段并不需要特别拘泥于细节,因为后面还会把删多的逻辑补回来,按照五步工作法的说法,如果最后没有补回来 10% 的逻辑,说明这个阶段删减的不够。

3.3 优化

在整个账单重构过程中,有几个难点我们专门提出来成立了专项进行优化

  1. 出账范围
  2. 商家账单中最基本的一个问题是给谁出账。老账单里起了好几十个任务在处理这个问题,经常会出现商户来问为什么没有出账,往往需要查半天才解释的清楚。重构时优化了该问题,明确了必须是签约了指定产品才能出账单,任务数相应减少到 10 个以下。
  3. 关联 jar 包

    商家账单中经常出现一笔昨日的流水需要关联多日之前的商品信息或者交易信息的诉求。这种跨天关联在离线odps的批处理框架下是比较麻烦且性价比很低的,在需要关联多日数据时面临着需要申请大量资源导致任务无法调起的问题。商家账单当前是使用一种jar包的方案来实现的,它的本质还是离线跨天关联,只是优化了并发逻辑,把一个大任务拆分成多个子任务发到 odps 跑。

    这次重构,我们提出离在线融合方案,利用在线可以笔笔查,性能好速度快的优势,使用 udf 调用在线http接口进行查询。考虑到在线查询可能会有失败的可能,对于失败的少数数据再用离线跨天关联的方式进行查漏补缺。

    目前这个方案还在研发中,预计可以大幅降低相关任务的计算成本,进一步提高出账的时效性。

  4. 离线灰度方案

    作为一个面客类产品,如何在离线实现像在线一样的变更三板斧从而减少对客影响,是一直困扰着所有离线同学的一个难题。本次重构中,我们做了一点尝试。我们的核心思想是:离线任务只跑一次但算两套值,并通过一个控制模块来控制哪些账号取原始值,哪些账号取灰度值。

    如下图所示,我们跑一次任务,把线上值记录在因子宽表的强字段收入金额和指出金额中,把灰度值记录在灰度扩展字段中,不同的值经过相同或者不同的加工规则,产出两个账单对客值净收入金额和灰度扩展字段中的净收入金额,最后通过一个控制模块来决定哪些账号要用灰度值。

    image.png

图5:离线灰度方案

  1. 稳定性自愈方案

    商家账单有几千个任务,但我们依赖的这套离线批处理的模式里又有很多不确定的因素:odps 的软件问题,底层计算集群的机器抖动,槽位占用,在线压制等,所以每个月总有那么几十个报错或者变慢的任务需要人工处理。在本次重构过程中,我们联合蚂蚁大数据部相关团队上线了报错自动重跑和变慢自愈恢复等两个稳定性自愈方案。

    报错自动重跑方案的核心是系统自动识别运行日志中的关键词,除非是明确不可重跑的报错(如数据质量问题,权限问题等),都会由调度系统拉起来重跑,实际运行过程中还需要综合考虑基线余量等要素。目前报错自动重跑方案每个月可以减少商家账单几十次的报错处理,减少 4-5 天的起夜值班。

    变慢自愈方案的核心思想是识别相关变慢任务并自动 copy 到双跑链路执行。若双跑任务执行期间原链路恢复,则不做处理;若双跑链路执行完成,原链路仍未完成,则杀死原链路任务,将双跑结果注入原表,将任务置成功。

图 6:变慢自愈方案

3.4 加速

在第二步删减模块我们只关注于核心字段的核心逻辑,一方面存在核心字段逻辑删多了的问题,另外一方面需要把其余个性化字段也补上。在第四步加速中,我们需要通过一定的方式开始回补,并且这种回补相比第二步而言要高效的多。

我们的办法是找一个牵引指标,小步快跑,快速迭代。当主逻辑搭建的差不多了以后尽快把脚本发布上线,并起一个新老账单对比任务,通过对比来发现新账单逻辑上存在的问题,对于缺失的部分快速补上。这里面的核心是要有一个牵引指标,在账单重构过程中,我们引入了商户可切流比例这样一个指标,计算公式如下

商户可切流比例=所有流水的所有字段都比对通过的商户数/总商户数*100%

以资金账单为例,商户可切流比例从第一版的 41% 经过大概 10 次迭代上升到了 85%,后又经过一段时间的精细化调整,目前为 99.3%。在这个过程中,我们一方面修复了代码中的 bug,另外也基本上把删多了的有用逻辑进行了回补。这种目标驱动的针对性查漏补缺的做法相比第二步的正向推进要高效的多。

图 7:资金账单的迭代次数和商户可切流比例

3.5 替换

五步工作法的最后一步是自动化替换人工,在账单场景中我们姑且取替换之意。在商户可切流比例高于 95%,且新账单的时效性等问题基本优化完全之后,我们就开启了新老账单的替换工作。优先切换核对通过且经常有下载使用的商户,这样做一方面可以得到商户的反馈,另一方面不因为长尾的逻辑优化影响切流。

4. 重构效果

重构的效果总的来说是满足预期的。以下为几个方面的效果

  • 复杂度

我们用任务数来衡量复杂度,资金流水账单的复杂度下降了 60% 以上,交易订单的复杂度也下降了47%

  • 时效性

资金流水账单时效性较老账单提升 1.5 小时,交易订单提升 1 小时

  • 成本

    存储和计算成本较老账单下降 1/3 左右,每年节省上百万的计存成本

  • 准确性

汇总,月,历史等账单均从日明细加工而得,不再会有内部不统一的问题

  • 运维/理解成本

代码耦合度大幅降低,账单整体的理解成本从半年到1年下降到 1 个月左右

5. 总结反思

站在现在这个时间点,我们认为有那么几点是值得总结的

1) 复杂度是各种问题的源泉

商家账单的各种准确性,时效性以及高可用问题,归根到底是因为业务逻辑过多,架构腐化,导致整体复杂度急剧飙升,造成今日想改也改不动,想维持也维持不了的尴尬局面。我们必须在日常迭代中高度重视复杂度控制问题,不图一时之快,尽量不给后人留坑。

2) 很多复杂度是没有必要的

账单重构的经验表明,对于一个发展了多年的系统,很多复杂度是没有必要的。今日之所以可以降低复杂度,一方面是因为过去很多逻辑现在已经失效了,另一方面是因为后人对于业务的理解有了新的认知,可以用新的方法来复现来重做相关功能。

复杂度的降低带来的好处是方方面面的,就商家账单而言,最直观的就是时效性的提升,从而带来基线稳定性的提升,降低起夜压力。其次复杂度的减少降低了运维和编码成本,可以进一步减少准确性问题。当然,用现在流行的话讲,这不是一种“防御性编程”,不再需要半年到1年的时间才能熟悉账单的工作,一个略有经验的同学,可能1个月左右就能上手账单业务。那是否要担心因此工作就会被替代呢?我们想是没有必要杞人忧天的,如果一个工作要通过刻意把事情变复杂才能形成壁垒和核心竞争力,那么这样的工作是不值得为之奉献的。

3) 拆解事情很重要,节奏感更重要

重构商家账单是一件有些复杂的事情,面对这样一团乱麻般的代码,从何处下手,要拆解出哪几件事情来,每件事件的交付物应该是什么,这样的拆解固然很重要。但更重要的是节奏感的把握,同样是做这些事情,哪个阶段先重点做什么工作,是细致做还是粗略做,这种节奏感的把握更为重要。因为如果节奏不对,就会在某个阶段发现事情无法快速推进下去,时间一久就会受到一线同学以及主管等质疑。要是节奏对了,每个阶段都能看到一些希望,那么一件复杂的事情便会推行的比较顺利。

4) 需要进一步降低重构这件事的成本

尽管如此,我们还是耗费了几百人日来做账单的重构。我们有那么多的场景值得重构,整个社会上也有非常多的公司有这种重构降本增效的诉求。是否有可能把重构的过程流程化,甚至是产品化,从而大幅降低重构这件事的成本?这是重构这件事给我们的遗留命题。

5) 数仓同学未来的两个发展方向

在转岗到支付宝数据部门的时候,有一位高年级的同学曾经问我如何看待数仓同学的上升空间/发展路径问题。经过这一年多在商家账单的一线工作,尤其是这大半年来专职投入重构工作的经历,我想可能有如下两个方向

a) 专业的数据技术专家

数据技术专家主要专注于通过代码优化,架构优化等方法,降低一套数仓任务的复杂度,获取时效,准确,计存成本等方面的收益。商家账单重构就是典型这类场景,这个发展方向的价值收益比较好衡量。未来的核心竞争力在于是否可以借助AI的力量把重构优化这件事的成本降低,提升效率。

b) 全局的数据架构师

全局的数据架构师更关注的是信息架构的问题,要解决的是数据生产者和数据消费者之间的信息差问题。我们常常可以听到业务同学抱怨数据不准,不好用,听到算法同学说没有优质的数据供给。殊不知其实要做一份好的数据资产其实是有比较高的门槛,需要对业务,架构,信息流转的方式等都有比较深入的理解,才有可能做出一份好的数据。但在实践中我们发现,造成这种门槛的一个重要原因是因为作为数据生产者的系统研发同学并不了解作为数据消费者的数仓同学的痛点,有些问题其实在数据生产者略作改动就可以给数据消费者减少极大的成本。数据架构师就需要致力于解决这样的问题。我们很难具象的衡量这样的改动带来的收益,但可以肯定的是这些细小的改动会润物细无声的降低做一份好的数据资产的门槛,进而真正的发挥数据要素乘数效应,助力业务发展。


作者:支付宝体验科技
来源:juejin.cn/post/7347912334700789779
收起阅读 »

10 天的开发量,老板让我 1 天完成,怎么办?

大家好,我是树哥! 昨天,我在文章《业务开发做到零 bug 有多难?》和大家聊了下影响零 bug 的一些因素。其中,我提到了开发时被压缩工时,应该怎么做。今天,我们就来聊聊这个话题。 只要工作过几年的小伙伴,必然会遇到过背压工时的情况。面对这种情况,不同的工作...
继续阅读 »

大家好,我是树哥!


昨天,我在文章《业务开发做到零 bug 有多难?》和大家聊了下影响零 bug 的一些因素。其中,我提到了开发时被压缩工时,应该怎么做。今天,我们就来聊聊这个话题。


只要工作过几年的小伙伴,必然会遇到过背压工时的情况。面对这种情况,不同的工作年限、在不同的公司、不同的团队氛围下,都会有不同的反应。如果你是一个刚刚毕业的萌新开发,很大情况下你会选择自己加班服从。甚至加班都完不成的情况下,你还吭哧吭哧不出声。


最后等待你的结果就是 —— 成为被复盘的对象,被批评。那么如果遇到了开发时间被压缩,或者被质疑的情况下,我们除了默默加班接受之外,还能做些什么来让自己没那么苦逼吗?


在我看来,自己一个人傻傻加班是下下签,是最后实在没办法才做的无奈之举。一旦有其他选择,你都不应该提出自己加班加点做完。那么,到底有什么办法可以解决工时被压缩这一问题呢?


解释工时构成


如果你的开发时间被压缩,那么较大可能是 leader 质疑你评估出的工时。假设你的工时评估并没有问题,那么就是你考虑到了一些风险点,而你的 leader 并没有考虑到。毕竟这也很正常,对于一个很久没有写代码的管理者来说,其会习惯性地忽略一些细节性的东西。


这个时候,你要做的不是胆怯地接受。而是要主动去找 leader ,跟他解释工时是怎么评估出来的。你考虑到了某些风险点,为什么是这么多工时。如果你的 leader 不是傻子,那么相信他会接受你的解释。但这里要注意的是,解释的时候记得要语气好些,不要怒气冲冲地找别人,不然话没说然就吵起来了。


减少需求内容


假设你和 leader 已经进行了友好地沟通, leader 也认可了你的评估时间。但是他说:没办法,老板就要求那个时间点做完,没办法给你更多时间了!


这时候,萌新小白就会老老实实回去座位上加班,最后还是干不完被批斗。但对于职场老油条来说,他就学会与 leader 以及产品沟通 —— 能不能少点需求内容。例如:我们要做一个员工列表,那是不是只做列表就可以,不用做筛选和搜索了?员工详情是不是也可以先不走了?


老板可以指定最终完成的时间,但是他基本不会干涉到具体的细节上面。这时候就给我们留下了沟通的空间,这也就是作为开发的你可以争取的东西。对于一个有经验的产品经理来说,如果研发给他提出了减少非核心功能的诉求,他一般也会答应的。


申请更多资源


如果产品说:不行,我们每个功能点都得做,一点需求都少不了!


这时候你可以再向你的老板提出诉求 —— 申请更多资源。


前面你也解释过工时的构成,做这么多功能确实需要这么多时间。如果最终上线时间不能推迟,那么就只能投入更多的资源了。


在这种情况下,如果公司还有富裕的研发资源,那自然会优先考虑你这边的诉求。对于你来说,你的研发压力也自然变小了。


分摊开发压力


如果实在又申请不到更多资源,这个项目又只能由你们团队 5 个人来完成,怎么办?


很多时候,不同开发人员的开发压力不一样。可能你开发压力比较大,其他人开发压力比较小,这时候你可以提出 —— 是否可以让其他小伙伴帮忙做点工作,这样可以减少一些压力?


我想,如果你的 leader 也应该会考虑你的诉求。千万不要自己明明完成不了,还要硬抗。到最后加班干了几个星期,需求还是完成不了,不仅辛苦的付出得不到理解,还被批斗。那可就真的是赔了夫人又折兵啊!


千万不要觉得这种情况不会发生,在我去年工作的时候,就发生了这样一个事情,我也是很同情那位同学的。如果那位同学能看到这篇文章,那么或许他后面就不会踩坑了吧。


推迟上线时间


上面说得是最终上线时间无法变更的情况,但很多时候并没有这种倒排需求。很多需求的上线时间并不是一成不变的,你只要给出足够合理的解释,也都是可以沟通的。


因此,如果在上面的沟通方法都行不通的情况下,你也可以沟通看看是否可以推迟上线时间。毕竟相对于研发速度来说,研发质量肯定更加重要。


终极绝招


大多数情况下,如果你能合理应用上面提到的几种沟通方式,被压缩工时的问题一般都能解决。但有些小伙伴会问:那如果真的所有办法都失效了呢?那怎么办?


其实,大多数情况下,不太可能到了需要使用绝招的地步。但如果真的到了这一步,那你就做好「殊死一搏」的准备,用上这个绝招吧 —— 调预期、表态度。


调预期,就是给你的 leader 打预防针,提前告诉他这样做的后果就是 —— 质量差、很难做得完。如果他还是这么坚定地推进,那么如果真的做不完,相信他也理解,不会太过于责怪你。


表态度,就是得加加班。如果你之前已经说了压力很大,甚至加班都做不完。那么你至少还是得表表态度,不能像往常一样早早下班,这样即使最后搞砸了。由于你态度还算端正,还不至于被责怪得太狠。但如果你要是又说做不完,又每天早早下班,那别人就觉得是你态度问题了。


走到这一步,实属是无奈,但这也是最后的保命之举了,除非你不想在这干了。


总结


今天分享了几种沟通解决「被压缩工时」的方法,包括:



  • 解释工时构成

  • 减少需求内容

  • 申请更多资源

  • 分摊开发压力

  • 推迟上线时间


本质上来说,就是不要自己一个人傻傻地抗压力,不要让自己背负着太大压力。我们要明白自己能做到什么程度,而且不要早早把「自己加班」这一最后的保命、卖惨利器祭出。他应该是自己的保命技能,而不是为别人锦上添花的技能。


特别是,不要因为赶进度、赶工时,而去牺牲开发质量。因为如果你这么做了,后果就是你付出了很多时间和精力,最后你会在项目复盘会上检讨 —— 为什么你的功能代码质量这么差。这是另一个话题了,后续有时间我们继续聊。


希望大家都能够活学活用,下次在和 leader 以及产品沟通的时候,用上这些沟通技巧吧!希望大家都不要加班,准时下班!


如果你觉得今天的文章对你有帮助,欢迎点赞转发评论支持树哥,你的支持对于我很重要,感谢大家!


作者:树哥聊编程
来源:juejin.cn/post/7348289379055140903
收起阅读 »

业务开发做到零 bug 有多难?

大家好,我是树哥,好久不见啦。作为一个工作了 10 多年的开发,写业务代码总是写了不少的。但你想过做到零 bug 吗?我可是想过的,毕竟我还是有点追求的。不然每天都是浑浑噩噩地过,多没意思啊。大概在一年多前,我给自己立下一个目标 —— 尽量将自己经手的业务需求...
继续阅读 »

大家好,我是树哥,好久不见啦。

作为一个工作了 10 多年的开发,写业务代码总是写了不少的。但你想过做到零 bug 吗?我可是想过的,毕竟我还是有点追求的。不然每天都是浑浑噩噩地过,多没意思啊。

大概在一年多前,我给自己立下一个目标 —— 尽量将自己经手的业务需求做到零 bug。不试不知道,一试吓一跳,原来零 bug 还真的还不容易。今天,树哥就跟大家分享关于「业务开发零 bug」的一些思考。

要做到业务开发零 bug,其实挺难的。这涉及到非常多方面,有些方面可能还不只是你能控制的,例如:产品 PRD 详尽程度,产研组织的稳定性等等。经过一段时间的思考与摸索,我自己总结出一些影响因素,分别是:

  1. 产品需求文档的清晰程度
  2. 需求的复杂程度
  3. 开发人员的细心程度
  4. 开发人员是否详细自测过
  5. 开发人员对项目的熟悉程度
  6. 开发人员开发时间是否充足

针对上面说到的影响因素,我们一个个详细聊聊。

需求文档清晰程度

对于研发、测试人员来说,他们获取信息的源头就是产品的 PRD 文档。因此,需求文档是否写得清晰、明确,就显得非常重要。

如果产品自己对功能都不了解,那么输出的需求文档肯定「缺斤少两」,到时候就是边开发边补充需求,甚至是在测试过程中补充需求。遇到这种情况,想要做到零 bug 真的非常难。

因此,清晰明确的需求文档,是我们实现业务开发零 bug 的重要前提。如果这个前提保证不了,那要做到零 bug 真的很难。毕竟想做成啥样都不知道,程序员又不是神仙,咋能猜出你想要什么。但这块内容,更多是对于产品人员专业能力的要求,开发人员无法控制。

在一些公司,会再需求评审之前先对需求文档进行一次初审,筛除那些有明显重大问题的需求,这样可以减少一部分劣质需求。

但初审的作用还是有限的,它没办法对功能的细节做较多的判断。很多时候恰恰就是一些功能细节的缺失,导致了一些 bug 的诞生。

需求的复杂程度

需求的复杂程度,对于实现业务开发零 bug 也有很大的影响。举个简单地例子:一个改文案的需求,和一个完全重新做的功能。

这样的两个需求,其复杂程度差别很大,肯定是改文案的需求实现业务开发零 bug 的难度低很多。对于一个完全重新做的功能,要做到完全零 bug,对于开发人员的要求非常高。

对于越复杂的项目,零 bug 的可能性就越低。因此,很多项目为了追求产出功能的高质量,会采用将功能点拆得非常细的方式,来减少单个需求的复杂度。

笔者公司在去年做过这个尝试,确实是可以较大地提高产出功能的质量。

细心程度

前面说到需求文档的清晰程度很重要,这取决于产品人员对于业务的理解程度,以及对于对于功能的熟悉程度。开发人员的细心,就像是一个质检关卡一样,在开发之前就对产品的需求内容进行详尽的思考与提问。

对于粗心的开发人员来说,其可能不看需求文档就直接参加需求评审,等到开发的时候边写代码边看需求文档,其写得代码也是一边熟悉需求一边改。这样写出来的系统功能是比较差的,没有一个统一、全局的设计与思考,很容易在细节处发生问题。

一个细心的开发人员,其会在评审之前就详细阅读需求文档,甚至会前前后后翻阅好几次。他甚至会逐字逐句地阅读,弄懂每个文字、句子的意思,甚至有时候会让你觉得他是在玩文字游戏(但不得不说,确实有必要细致一些)。

最后会联系上下文思考功能的合理性。如果发现一些不合理的地方,他会积极与产品沟通反馈,以确保其对于需求的理解,与产品经理对于需求的理解是一致的。

通过对比,我们知道细心的开发人员对于产品经理来说,是一个莫大的帮助,可以帮助他查漏补缺,让其对于功能的考虑更加细致、严谨。

这里的开发人员不仅仅指的是后端开发人员,也包括前端开发、移动端开发,他们都会从不同角度提出问题。

对于后端开发人员来说,他们可能会提出性能问题。对于前端开发以及移动端开发同学,他们可能会提出交互问题、样式统一等问题。

简单地说,细心的开发人员可以弥补需求文档的缺陷,从而让大家对于需求的理解更趋于一致,从而减少 bug 的发生。因此,开发人员的细心程度也是决定业务开发能否实现零 bug 的关键因素!

是否详细自测过

即使写过 10 多年代码的开发人员,刷 Leetcode 也不敢说 bug free 一把过,对于更加复杂的业务代码更是如此。因此,要做到业务开发零 bug,其中一个很重要的操作便是 —— 自测。

自测可以帮你再次检查可能出现的问题,从而提高零 bug 的概率。对于我而言,我习惯性在自测的时候再次对照一遍需求文档,从而避免自己遗漏一些功能的细节点。

对于自测而言,业界有很多种自测方法,包括:单测、集成测试、功能测试。一般情况,建议自己选择适合自己的自测方法。

很多时候,功能测试是相对来说性价比较高的方式。除此之外,自测的详细程度也根据实际情况有所不同,例如有些人只会测试正常情况,但有些老手会测试一些边界情况、异常情况。

毫无疑问,你越能像测试人员一样测试,你的提测质量肯定就越高,bug 当然也就越少。

对项目的熟悉程度

这里说的项目熟悉程度,既指技术层面的熟悉程度,也指业务功能层面的熟悉程度。

技术层面的熟悉程度,指的是项目之间是用什么技术栈搭建的,你对这些技术是否都熟悉。举个很简单的例子,项目中采用了微服务的方式进行调用,那么你是否清楚是什么微服务调用?

如果采用了 ElasticSearch 进行搜索,那么你是否对 ElasticSearch 有一些了解,知道一些基本使用及最佳实践?等等。

这些算是技术层面的熟悉程度,你对这些越熟悉,你在技术层面发生问题的可能性就越小。

业务功能层面的熟悉程度,指的是你对项目其他模块的业务是否熟悉。例如你经常负责 A 模块的功能,你对 A 模块肯定很熟悉。

但下个迭代你就要去做 B 迭代的需求了,这时候你肯定不是很熟,相对来说出错的可能性就更大一些。

无论是技术层面,还是业务层面的熟悉程度,都会随着你做了更多的需求,变得更加熟悉。到了后面某个阶段,你基本上就不存在踩坑的问题了,也为你业务开发零 bug 奠定了基础。如果你是一个刚刚进入公司的新手,那么做到零 bug 还是很难的。

开发时间是否充足

开发时间是否充足,决定了你是否有充足的时间去熟悉需求,去和产品经理确定细节。有了充足的时间,你也才能有一定时间去进行更详细的自测。更为关键的一点,有充足的时间,你写代码才能写得更好。因此,开发时间是否充足是很重要的。

在实际的开发过程中,会因为各种各样的原因,其实并没有办法给你留出特别理想的开发时间。这时候该怎么办?有些人选择接受,去压缩自己的时间。

有些人则会选择去沟通,或者协调资源,保证自己有充足的时间。其实,正确的做法还是第二种,这样会更好一些。

这需要开发人员有更强的综合能力(沟通、协调能力),但并不是每个开发人员都具备的。关于这点,又是可以聊的一个话题 —— 当你的需求被压缩工时的时候,你应该怎么做?这里暂不展开,后续有时间可以聊聊。

简单来说,开发时间是基础,没有合理、充足的时间保障的话,要做到业务开发零 bug 是不可能的事情。

总结

要做到业务开发零 bug,其实就是要消除功能开发过程中的所有不确定性,包括:需求功能的不确定性、自己写错代码的不确定性等等。而发生这些不确定性的地方,可能就有:

  1. 产品需求文档的清晰程度
  2. 需求的复杂程度
  3. 开发人员的细心程度
  4. 开发人员是否详细自测过
  5. 开发人员对项目的熟悉程度
  6. 开发人员开发时间是否充足

除了上面说到的 6 个影响业务开发零 bug 的因素之外,肯定还有其他影响因素。

你能想到什么影响业务开发零 bug 的因素吗?

欢迎在评论区留言与大家分享。

好了,今天的分享就到此为止。如果你觉得今天的文章对你有帮助,欢迎点赞转发评论,你的转发对于我很重要,感谢大家!


作者:树哥聊编程
来源:mp.weixin.qq.com/s/XqCD9-epYHstWD3CS7hLEg
收起阅读 »

做好离职管理,享受非凡人生

近年来,职场竞争越来越激烈,每个员工都希望通过努力工作,赢得领导的认可和提拔机会。 然后,不可否认的是,有人粉墨登场,就有人卸妆离场。离职是职业生涯中一个重要的转折点,它不仅是结束一段工作关系,也是展示个人素质和职业态度的重要时刻。 人们常说“离职见人品”,这...
继续阅读 »

近年来,职场竞争越来越激烈,每个员工都希望通过努力工作,赢得领导的认可和提拔机会。


然后,不可否认的是,有人粉墨登场,就有人卸妆离场。离职是职业生涯中一个重要的转折点,它不仅是结束一段工作关系,也是展示个人素质和职业态度的重要时刻。


人们常说“离职见人品”,这句话凸显了离职时人品的重要性。而对于某些管理岗位,往往在招聘时,都是会背调的。


离职时的表现往往能够反映出一个人的职业素养和道德水准。


在离职过程中,一个有良好人品的人会以积极、负责的态度对待工作交接,尽力确保工作流程的顺畅进行,不给公司和团队带来不必要的麻烦。


他们会与上级和同事进行充分的沟通,表达对公司的感激之情,并保持良好的合作关系。


相反,一些人在离职时可能会表现出不良的行为。


他们可能会消极对待工作交接,甚至故意隐瞒重要信息或破坏工作进度,给公司和团队带来困扰。不要认为你在这家公司做的不爽,你就也想让公司不爽,这样的行为不仅缺乏职业道德,也可能对个人的声誉和未来的职业发展产生负面影响。


我身边一个真实的案例,我的前同事(主管级别)因为不服空降领导,在持续了三个月与领导发生冲突和争吵后,愤然离职甩脸色,再其离职后,仍发邮件给公司高层打报告。现在他基本在杭州很难混下去,因为背调基本上打电话过来给目前的领导,询问其人品,结果可想而知了。上个月还听到领导跟我交流,说某某公司找他背调前同事。


那么,在离职时如何展现良好的人品呢?我们如何体面的告别自己的工作呢?


01. 提前通知


在离职前,提前向上级和同事发出离职通知是一种负责任的行为。


这样做可以给予公司足够的时间来安排工作交接,确保工作流程的顺畅进行。


通过提前通知,公司可以有足够的时间找到合适的人选来接替你的职位,避免因你的离职而导致工作的中断或延误。


同时,这也为你的同事提供了准备和适应的时间,以便他们能够顺利接手你的工作职责。这样的做法不仅展现了你的职业素养,也有助于维护良好的人际关系。


2. 积极配合


在工作交接期间,积极配合同事和上级,确保工作流程的顺畅进行。比如:
1、制定详细的交接计划:与上级和同事一起制定详细的交接计划,明确交接的内容、时间和责任人。这样可以确保交接工作有条不紊地进行。
2、分享工作文档和资料:将你的工作文档、资料和相关信息整理好,并与同事和上级分享。这将帮助他们更好地了解工作的细节和进展,以便顺利接手。
3、提供培训和指导:如果同事需要,你可以提供培训和指导,帮助他们熟悉工作流程和项目。这将有助于他们更快地适应新的工作职责。
4、积极回答问题:在同事和上级有疑问或需要帮助时,积极回答问题并提供支持。保持沟通畅通,确保他们能够顺利进行工作。
5、参与重要会议和项目:如果可能的话,参与一些重要的会议和项目,以便更好地了解工作的最新情况,并在必要时提供帮助。


3. 保持联系


离职时,你要向公司领导和同事表达感激之情,感谢他们在工作中给予的支持和帮助。不要因为工作的事情,搞得自己不开心。
还有你一定要清楚,离职了不是永别了,在你工作中积累的同事和领导关系,都是你日后在这个社会中的潜在资源,离职时把关系维护好,说不定哪天,他们能在某个地方帮助到你。


离职后,与前同事和上级保持联系,建立良好的人际关系。


edc24cf0a4794418a044541d72cb2cc4_3.png


4. 不抱怨不诋毁


静坐当思己过,闲谈莫论人非。在离职过程中,不要抱怨公司或同事,也不要在背后诋毁他们。抱怨和诋毁只会让自己显得狭隘和小气,对于未来的职业发展也没有任何好处。即使在离职过程中存在一些不愉快的事情,我们也应该以成熟的方式处理,保持良好的沟通和合作。


5.结语


总之,“离职见人品”这句话提醒我们,在职业生涯中,我们的行为和态度不仅影响着当前的工作环境,也会对未来的发展产生深远的影响。在离职过程中,我们应该保持积极的态度,不要抱怨或诋毁公司或同事。学会感恩,以成熟的方式处理事情,保持良好的人际关系,这些都是我们未来职业发展的宝贵财富。因此,无论离职与否,我们都应该始终保持良好的职业素养和道德标准,以展现自己的优秀品质。


676153ad0a7146a796cc55819a5999bd_1.png


作者:陆理手记
来源:juejin.cn/post/7347910130711035913
收起阅读 »

号外:小程序获取手机号要付费了 0.03元/次 !😒

前言 今天无意中得知了 v2ex.com 打不开的原因,原来规则判断走的是国内线路,需要启用全局连接,切换后就第一次成功访问该站点,没想到就在头条发现了这么一条吐槽微信小程序的消息 获取手机号要收费了,一度以为是假消息,经过验证,发现竟然是真的。 从微信开发...
继续阅读 »

前言


今天无意中得知了 v2ex.com 打不开的原因,原来规则判断走的是国内线路,需要启用全局连接,切换后就第一次成功访问该站点,没想到就在头条发现了这么一条吐槽微信小程序的消息 获取手机号要收费了,一度以为是假消息,经过验证,发现竟然是真的。


截屏2023-06-26 21.59.04.png


从微信开发文档中确实发现了这条收费信息,貌似是今天刚更新的,然后就在刚刚,收到了官方消息通知。


截屏2023-06-26 19.53.48.png


关键信息


目前的获取手机号组件,将从 8月26号 开始,以 0.03元/条 的价格收费,每调用成功计数一次。


每个小程序总共赠送 1000 次免费额度(不是每月送一次哦),注意这 1000 次是包含开发版、体验版、正式版的。


除了现在的获取手机号组件外,腾讯又推出了一个新的组件,也是用来获取手机号的,区别在于是实时获取用户最新的,可能之前的组件过去的是有一段时间内的缓存数据?这个组件价格为 0.04元/次


以上两个组件具体收费,貌似是可以按照套餐来购买的,具体方案可以在小程序后台的付费模块查看。


充值或者购买后,可以在小程序后台付费菜单模块,查看额度,以及每日的使用情况,当费用达到临界值时候,也会通过消息提醒你充值续费的。nnd真贴心


截屏2023-06-26 19.49.30.png


截屏2023-06-26 19.51.38.png


总结下


还有两个月时间,可以开始梳理自己公司的小程序了,然后找老板讨论方案,该掏钱掏钱,该改方案就改方案吧;


其实想想,企业项目的话公司花钱,自己也不用心疼,个人项目的话,估计也没几个用户,更花不了几个钱,对程序员来说,没啥影响;


不过腾讯这波操作,感觉像缴人头税一样,难道是经济不好,开始拓展创收渠道了?会不会以后每一个微信生态 api 都要单独给钱才能用呢 😒?


据说现在全网小程序已经突破 700万个了,假设每个先充值 1000 块,那就是70亿啊!!这波操作,属实做到了我曾经想做而做不到的事,全国人民给我1块钱,我立马成亿万富翁了,只能说 666, 服了。




作者:Ethan_Zhou
来源:juejin.cn/post/7248909699961634853
收起阅读 »

4年零4天,我从毕业后的第一家公司离职了

写在前面 从上家公司离职已经有一段时间了,当我打开备忘录翻看以前每天的todolist,成长历程历历在目,也觉得有必要写一篇文章对我毕业后的第一份工作做一个阶段性的总结。 离职原因 我的第一家公司是杭州某大型车企旗下的一家网约车公司,19年11月份拿到校招o...
继续阅读 »

写在前面


从上家公司离职已经有一段时间了,当我打开备忘录翻看以前每天的todolist,成长历程历历在目,也觉得有必要写一篇文章对我毕业后的第一份工作做一个阶段性的总结。


image-20240224093538751.png


离职原因


我的第一家公司是杭州某大型车企旗下的一家网约车公司,19年11月份拿到校招offer就开始进入公司实习了,2020年6月份正式转正,在2023年11月底离职,所以满打满算应该在这家公司呆了有四年的时间。


至于为什么离职,有以下几点原因:



  1. 首先是感觉到个人成长受限。不知道大家有没有同感,在一家公司时间呆久了之后,就有一种温水煮青蛙的感觉,看到一些老青蛙,就像看到了未来的自己,会有危机感。

  2. 其次是我个人原因,想进大厂。由于自己的学历在市场上不是很有竞争力,希望通过大厂经历能够稍微弥补一下,方便为自己以后长远的职业生涯做打算。

  3. 当然公司的原因也有,首先是公司的管理层和公司文化发生了变化。简单来说,就是从之前的车企文化变成了"福报文化",就让我有一种“在哪儿卷不是卷?”的想法。


    其次,公司的战略也让我感觉到一种危机感,从各方面的信息来看,现在是一种破釜沉舟的心态,但是破釜沉舟了这么久,也没有看到成效,反而是公司的一部分员工因为所谓的战略,需要将办公地点迁到苏州。虽然还没有轮到我们部门,那么如果真的有那么一天,我还是得准备离职,还不如早做打算。



成长历程


在这家公司一共有过两次晋升,一次是在2022年,一次是在2023年,算上普调,应该是有过三次涨薪。


刚开始进入公司的时候,是以实习生的身份,那时候我刚从一家几百人的小公司实习结束,也是我第一次亲身经历了比较正规的研发流程和研发规范。刚开始的时候,每天都有很多低级问题要问,和测试、产品同学沟通起来也是十分的不流畅,加上当时刚好赶上了疫情,在家办公了一段时间,好在实习的表现还算满意,我的4个月实习让我免去了试用期,拿到毕-业-证以后直接转正了。


毕业后分配到了营销小组,这是我第一次做To C的业务,经常会出一些线上问题,收到用户的投诉,当时的老板对于线上问题的忍耐程度很低,很小的问题都会被无限放大,导致我当时在做需求,需求的上线都是处于一种极度紧张的状态,一旦出现线上问题,都会默默的打开Boss 直聘,做好找下一份工作的准备。


在之后的1 ~ 3的工作经历中,我渐渐找到了工作的节奏,以及如何应对一些人际关系,处理起线上问题也比以前镇定多了。第二年和第三三的绩效都比较好,而且后来的某一段时间内,公司优化掉了大部分的测试同学,我们研发写的代码需要研发进行自测,我们的需求研发周期变成了研发时间 + 自测时间,我觉得这给了我们研发更多的Buffer,能把一个需求做的更好,甚至我经常能留出多余的时间来做一些okr相关的项目。


在离开公司的前半年时间,我的工作又发生了很大的变化,在完成日常的工作之外,我还积极参与了公司的游泳社团、羽毛球社团、篮球社团。分别在周二、周四、周五跟着公司的小伙伴一起参加体育运动,这对我的身体状况有了很大的改善。


这三年半有什么成长?



  1. 技术上的成长:技术上的成长当然是首位的。刚来实习的时候,这会写一些简单的jsx语法,后来在能完成公司的正常业务迭代之外,还参与了公司脚手架的建设,帮助解决一些框架上带来的问题。同时还有机会接触到APM监控系统的核心流程,对APM这个功能进行迭代。另外还有一些简单的BFF开发、低代码平台的开发、埋点核心链路的监控、微信/支付宝小程序...

  2. 心态上的成长:刚毕业的时候,心态是很脆弱的,经常会因为一些小事情,心里就默念:“不干了!”。现在的心态是:“挣钱嘛,受点委屈怎么了?”

  3. 时间管理上的成长:由于要在工作之外还要保证自己的健康状态、和个人成长。所以在时间管理上,我渐渐有了一套自己的管理模式。比如每周要锻炼多少次,最近一段时间要把这个知识点复习完毕,这个年度要去几个城市旅游,今年要学会游泳,等等。


    我甚至学会了利用地铁的通勤时间做一些知识点的复习、阅读书籍、做一些今天的时间规划之类的事情,我觉得是一个很大的成长。


  4. 学习能力的成长:毕业之前,我只会通过看视频来学习,看文字,看文档,我都很难学习到知识,经常遗漏一些关键点。现在我甚至很排斥看视频这种方式,觉得很浪费时间,很啰嗦...


健康状况


除了我的胃,其他都没有什么大毛病,这里要告诫一下大家一定要注意保护自己的胃,胃病真的想象的那么简单。


由于疫情期间在家里没怎么活动,加上暴饮暴食,饱腹后继续喝茶... 以及后来复工之后在公司天天吃外卖,导致我的胃经常胀气。中午午睡的时候顶的难受睡不着觉,晚上睡觉的时候肚子也胀胀的,需要起身好几次打几个嗝才能睡得着,对我的睡眠造成了很大的困扰。


期间也去医院看过,做过胃镜,吃过中药,但是效果不是那么明显。后来很长一段时间没有吃辣的,也按时吃饭,不吃夜宵,经常跳绳锻炼一下,渐渐有所好转。


面试历程


其实跳槽这件事情是我在一两年前就计划好的。在22年底的时候,其实就出去面试过,不过当时没有准备的特别充分,加上当时太天真,还是一副刚毕业时年轻气盛的样子,导致很多面试官对我的印象都不是特别好。




一些感谢的人


首先感谢一下我上家公司的几位直系上司。我呆过两个组,两个组长都对我十分不错,一位在我实习期间给了我很多引导,帮我快速熟悉公司的业务。另外一位则是在我成为正式员工之后,帮我担下了很多的责任,并且帮助我快速的成长,成功获得了两次晋升的机会,并且都顺利通过。


另外感谢一下我的专家,真的是一位特别好的人,从来不会PUA下属,总是会以过来人的角度给你一些很好的建议。


有没有什么要吐槽的


如果非有什么需要吐槽的,还是公司的文化吧。并不是说现在的文化有什么问题,我想吐槽的是变化。因为曾经美好过,所以当注入新鲜血液之后的变化,其实让很多经历过美好的人会有一些失望😂😂😂


写在最后


感觉这四年时间过的很快,从一个职场新人变成了拥有三年多经验的打工人。昨天晚上还在家里翻出之前入职培训时的一些合影,当时我记得校招入职的时候有54人,算上被优化和自己主动离职的,目前应该还剩下不到10人。


希望老东家越来越好,早点实现盈利上市!!!


也希望自己在下一份工作中能够快速适应,能够给N年后的自己也交上一张满意的答卷。


作者:枣仁
来源:juejin.cn/post/7339042131468697640
收起阅读 »

春天的痛与爱,教会了我善良

看了看天气预报,从明天开始天气就变暖了,路两旁的花也开了,有些树也冒出了新芽,再过一段时间,就可以真正意义上感受春天的气息了。昨晚做了一个梦,梦到了好多小伙伴,大家一起去爬山,因为还有几个妹子一起,所以我就像孙悟空一样这棵树爬一下,那棵树吊一下,以至于今天早上...
继续阅读 »

看了看天气预报,从明天开始天气就变暖了,路两旁的花也开了,有些树也冒出了新芽,再过一段时间,就可以真正意义上感受春天的气息了。图片昨晚做了一个梦,梦到了好多小伙伴,大家一起去爬山,因为还有几个妹子一起,所以我就像孙悟空一样这棵树爬一下,那棵树吊一下,以至于今天早上醒来后,全身酸痛,差点班都不想去上,此刻,打着字,手依然是酸痛的。


我感到有点后悔,因为现实中,我算是已经很少去装X了,但是梦里居然还是那个德行,不过想一想,这怪我了?梦啥我能决定吗?瞬间心里好受了一点,就当锻炼了吧,平时很少锻炼,梦里能锻炼一下也不错。


大概从明天开始后就不会再有多过分冷的天气了,所以这个梦就当做真正意义上春天的开场曲了,春夏秋冬这四个季节,我最喜欢春天,因为这个季节里有美好的回忆,也有令人痛苦的回忆。


我爷爷家门口有一片竹林,春天的时候,竹林里面会长很多竹蛋,竹蛋开花后就是竹荪,是很不错的美味,竹林下面是一条小沟,整个村子农作物灌溉的水都需要从这里过,而那会我们经常要去堵水,堵水的意思就是去几公里外的源头抢一点水,然后让水流向往村子里的小沟,途中不断有支流,直到流到自己家的田里。


从源头到我家田里大概有四五公里的路程,那会我经常顺着小沟走到田里,因为是丘陵地带,所以一直在半山腰上走,而山腰下面全是农田,到处都是一片绿油油的,那时候家里养了一只小狗,因为比较贪吃,名字叫做馋瓢,我偶尔还会带着它顺着小狗走,它经常还会捉到一些小野生动物。


那会对外界没有什么概念,连乡镇都没去过,只是在我爷爷家墙上的报纸上能了解一点,所以每当看到田野,高山的时候,心中都会产生一些幻想。


三年级是在乡镇上读书,那会拳皇97和三国战记2007特别风靡,于是那会我经常在游戏厅里打上几个小时,三国经常一个币打到通关,那会父母在浙江打工,后面他们回来直到我经常去打游戏,于是经常被骂,后面就很少去了。


不过狗改不了吃屎,虚拟的我玩不了就不玩,但但是现实中我可不放过,于是和一个比我小几级的同村小伙伴,两个用木棒自己做武器,我喜欢孔明,于是做了一把剑,他喜欢赵云,于是搞了一杆长枪。


那时候正是春天,我们两个每天都去别人家地里将菜和秸秆当作小兵,疯狂冲杀,于是经常被别人骂上好几个小时,现在回想起来,看着别人心疼的捡起碎了的蔬菜,真的觉得自己做了好大的孽了。


四年级的时候,捡到了一个类似于MP3那种小玩意,可以收音,于是我在租房子过去的坟头上收音,那会信号是很弱的,需要来回走动才能收到信号,就听了一些什么国际形势的东西,但是啥也不懂,只是觉得能够收入来自于外面的声音,就觉得很幸福,因为小镇上没有网吧,每次都会在坟头来回走几百次,坟头草都给别人踩没了,不过还好,春天里的生命力是无比顽强的,没了又会快速长出来。


我只在小镇待了一年半,但是那段发生在春天里的故事至今无法忘怀,因为都有点作孽,所以教学了以后我要善良一点。


到了县城读书后,因为南方的雨水比较多,春天和夏天经常水淹县城,那会我妈在街上买水果,每当下大雨的时候,我都赶快去给她收摊,记得有一次雨特别大,我给她收完摊子,看到路上好多被雨淋着的背篼(贵州的一种职业)。


于是回到家里,我搞了两把雨伞,冒着大雨就出门了,在街上遇到一个六十多岁的背篼,我就主动给他伞,然后送他回家,送他到家后,我就原路返回回家了,一路上水淹到了膝盖,还有电闪雷鸣,特别吓人。


回到家后,我全身湿透了,被骂了一顿,我记得我妈说:关你什么事,这么危险,你要是被水淹死了怎么办。


我当时哭着说:我还不是希望有一天你们遇到这种事情的事情,有人也能帮助你们,我有错吗?


那会特别委屈,多年后我才意识到,父母不是反对你做这种事情,而是太危险了,要是真的运气不好,被水冲走了怎么办。并且在我说出那句话时,她明显带有微笑。


后面她继续卖了四五年的水果,后面又卖烧饼,不知道在我没看到的时候,有没有人帮她推过三轮车,不过这一切都不重要了。


在后来初高中岁月里,我遇上了第一个喜欢的女孩子,并且也谈恋爱了,也是在春天,凌晨六点我家在她家门口等她,然后拉着她在东山下面跑步,呐喊,不过相处的时光依然很短,后面她辍学了,打了一个电话给我爸,叫我去她家,于是分手了。


那天夜里,我在东山下面转了很多圈才回去,后面的几个月里,也比较颓废,不过在那个年纪一切都情有可原。


几年后,我顺着火车路跑步到她家,然后做了一碗面条给我吃,瞎聊了很久,过了一年她就结婚,也是在春天,我不再顺着火车路跑步去她老家,而是骑着摩托车过去了,从那会起,我才算真正的放下。


后面,就没有再联系过了,东山的春天依然没变,只是那片土地变成了一个风景区,那些小路与菜地已经楼阁挺立,迎接了来自外地的游客,越来越多的人进来跑步,我刻在那颗核桃树上的字现在应该已经结痂了。


春是那么让人着谜,不单单是因为气候,更多的是因为它能带给我许多东西,让我从中反思,收获!


作者:苏格拉的底牌
来源:juejin.cn/post/7341282461203365922
收起阅读 »

中年程序员写给37岁的自己

笔者是一名程序员老司机,局限于笔者文笔一般,想到哪写到哪,胡乱写一通,希望通过文章的方式简单的回顾过去、总结现在和展望未来,顺便记录一下,方便以后总结。 你好,37岁👇 37岁的自己你好,接下来的几个“重要”是36岁的自己在过去一年中所得到的感悟,希望能够帮助...
继续阅读 »


笔者是一名程序员老司机,局限于笔者文笔一般,想到哪写到哪,胡乱写一通,希望通过文章的方式简单的回顾过去、总结现在和展望未来,顺便记录一下,方便以后总结。


你好,37岁👇


37岁的自己你好,接下来的几个“重要”是36岁的自己在过去一年中所得到的感悟,希望能够帮助37岁的自己更好的前行。


人生就是不停的打怪升级的过程,从2009年到今天,已经是第15个年头了,如果说程序员的职业生涯有20年的话,从现在算起至少还有5个年头可以继续拼搏。


春节快乐


在这里先祝各位春节快乐!


还有2天就到春节了,和前两年一样,还是一直在公司坚守到最后一天,也是利用最后比较清闲的时间,总结一下自己过去一年,把感想写下来,希望能够帮助自己更好的看清内心。


说真的每一年总结的时候,都会有不一样的收获。


运气很重要



再回头看自己15年成长的过程,运气和努力其实是各占一半,5分是不断努力的提升自己生存的技能,5分是在每个阶段也是很幸运遇到了能够帮助自己的贵人。但是这几年也很有感触,随着年龄的不断增长,运气很有可能是往后几年职业生涯是否能顺利的决定性因素。那什么是运气?比如你是否进入了一个没有被社会抛弃的行业,你是否正处于公司的重要赛道,你是否能和你的领导惺惺相惜,你正在做的事情是否能够发挥你的自身价值等等,以上这些当然和前期的努力是有关系的,通过你的努力让你有可能接受这一份运气的可能性,但是最终做决定的并不是自己。加入正好某个政策出现拯救了行业、正好公司的战略调整让你们部门还能招人、正好你领导看你顺眼并委以重任...那么请珍惜眼前,走好眼前每一步,努力付出,不辜负这一份运气!


写这篇文章的时候,正好在这家厂干满3年,这三年真是各种心酸,经历了整个公司业务的缩编裁撤,跌宕起伏,经历了团队连换3个领导,在最艰难,最焦虑的时候,选择了放下焦虑,在团队动荡的时候,更需要努力找机会向隔级领导证明自己,努力寻找过程中的那点不起眼的运气成分,同时做好准备,最坏的情况无非就是拿大礼包。但是如果就此躺平,那运气只会飘向其他人。终于在第三个领导的时候,运气来了,惺惺相惜的感觉出现了,逐渐被委以重任,这个时候就只管抱紧大腿往前冲就行了。


谨言慎行很重要


懂得在什么场合说什么样的话,以及能够听得懂别人的话外话,分得清对什么样的人应该说什么样的话,做到不给自己惹麻烦,不给领导惹麻烦。


程序员都是比较单纯的,和机器打交道最多,有一说一,不会拐弯抹角,这也使得我们在沟通或者有利用冲突的时候,经常是处于弱势的那一方,一不小心就会被别人当枪使,但我遇到的大部分同事都很nice的,也会有一些个卧龙凤雏,目前公司里确实遇到了一两个,有时候因为想用真心换真心,换来的却是冷枪暗箭,但俗话说吃一见长一智,以后和他们说话多留个心眼,不能被同一个坑埋两次吧。


这里举个例子,有一次我们有个研发主动去找产品同学,希望他们能够在下个需求时能从用户体验优化一些体验差的产品逻辑,我们可以加人优化,这个时候如果是靠谱的产品肯定是会一起配合梳理,但是我们的这个产品的领导真是个卧龙,这件事情传到他耳朵里,就变成了我们有资源也不给他们排期某某需求,反手就向上面老板投诉我们研发工作不饱和,真是能给人气死。这里并不是说我们同学没有情商,而是因为程序员所处的环境造就了我们,直面目标和结果的推进方式,容易全盘托出。我们喜欢沉浸在技术的世界里,这里所见即所得,绝对的平等,没有小人得志,没有尔虞我诈。


所以这里需要做到对人下菜,踩过的坑要记得,该设防的时候得设防,不能啥都说,拿不定主意时,少说多做。


身体健康很重要


作为家里的顶梁柱,可不能倒下,拼归拼,但身体健康还是要放在首位。35岁以后注意养生吧,现在发量真的比之前少了很多,头皮明显暴露在阳光下了,都是上有老下有小,没天的睡眠质量真的是大不如前。这个时候保持心情愉悦很重要,如果一只处于焦虑烦躁的状态,很容易导致身心疲惫,各种毛病就会接踵而至。由于睡眠不足,导致眼睛血丝严重,眼角膜出现问题,去年有大半年的时候都是往医院跑,在医生的叮嘱下,及时调整作息时间,工作生活保持适当躺平,保持心情愉悦,总算是没有往恶化的方面发展,以后只需要注意养生即可。


还是要保证适当的锻炼,但是不能过量,比如跳绳、跑步,对于我来说过量会膝盖疼,所以也不是很适合,每天适当的散散步是个不错的选择。


家庭和睦很重要


我们每天努力工作,就是为了多挣钱,为了给家人一个幸福美满的生活。在工作中难免会遇到很多委屈,心中自然会有很多不满,这时就需要自己找到发泄不满的方式,如果说家里人可以倾听,那可以和家里倾诉,如果不希望让家里知道,那可以通过刷剧、钓鱼、打球等方式,非常管用。


在过去这两三年,我媳妇是我很大的精神支柱,在21、22年团队业务动荡的时候,作为家里的顶梁柱,那时候压力山大,但她成为了我的坚强后盾,她鼓励我坚持学习充实自己,事情并没有到最坏的时候,只要时刻做好准备,其他的看运气,大不了就是失业,或许年纪大了可能会经历很长一段时间的空窗期,但慢慢找总能再找到工作的。她真正做到了陪伴、倾听、鼓励,没有不满、没有抱怨,这就是夫妻同心,其利断金。没有了后顾之忧,少了很多自身的精神内耗,学习效率、工作效率都会有很大的提升,随着公司业务的回暖,目前至少也算是在不断的稳步前进中。


现在媳妇有了、娃有了、房子有了、车子有了,这不就是人生最好的运气么,接下来我的目标其实就是努力经营好这个家,为他们遮风挡雨,家庭健康和睦比啥都重要。


适当旅游很重要


我们每天生活在高度紧张、快节奏的环境里,很容易把自己搞得紧张兮兮的,这个时候需要定期找时间出去放松一下,带上家人来一趟说走就走的旅行。慢节奏的旅行,不仅不累,还能促进家庭和睦,千万不要吝啬,该花钱的地方就得大胆的花。


今年一直想着找时间去一趟海南,所以等老大考试完第二天,立马就出发了。不过也许是许久没坐飞机了,竟然还忘记了45分钟不让值机的事情,也没有提前值机,一直排队托运,结果过时了没有完成托运和值机搞得还改签加钱体验了一把头等舱,但说实话北京坐飞机一路躺着去海南也是挺舒服的,空姐真的是服务周到。



1月初去海南温度刚刚好,完美的体验了一把反季节的旅行。


夕阳下的美好,这感觉又回到了十几年前弹恋爱的感觉:)。




作者:冲_破
来源:juejin.cn/post/7332381790341136384
收起阅读 »

外行转码农,焦虑到躺平

介绍自己 本人女,16年本科毕业,学的机械自动化专业,和大部分人一样,选专业的时候是拍大腿决定的。 恍恍惚惚度过大学四年,考研时心比天高选了本专业top5学校,考研失败,又不愿调剂,然后就参加校招大军。可能外貌+绩点优势,很顺利拿到了很多工厂offer,然后欢...
继续阅读 »

介绍自己


本人女,16年本科毕业,学的机械自动化专业,和大部分人一样,选专业的时候是拍大腿决定的。


恍恍惚惚度过大学四年,考研时心比天高选了本专业top5学校,考研失败,又不愿调剂,然后就参加校招大军。可能外貌+绩点优势,很顺利拿到了很多工厂offer,然后欢欢喜喜拖箱带桶进厂。


每天两点一线生活,住宿吃饭娱乐全在厂区,工资很低但是也没啥消费,住宿吃饭免费、四套厂服覆盖春夏秋冬。


我的岗位是 inplan软件维护 岗位,属于生产资料处理部门,在我来之前6年该岗位一直只有我师傅一个人,岗位主要是二次开发一款外购的软件,软件提供的api是基于perl语言,现在很少有人听过这个perl吧。该岗位可能是无数人眼里的神仙岗位吧,我在这呆了快两年,硬是没写过一段代码...


inplan软件维护 岗位的诞生就是我的师傅开创的,他原本只是负责生产资料处理,当大家只顾着用软件时,他翻到了说明书上的API一栏,然后写了一段代码,将大家每日手工一顿操作的事情用一个脚本解决了,此后更是停不下来,将部门各种excel数据处理也写成了脚本,引起了部门经理的注意,然后就设定了该岗位。


然而,将我一个对部门工作都不了解的新人丢在这个岗位,可想我的迷茫。开始半年师傅给我一本厚厚的《perl入门到精通》英文书籍,让我先学会 perl 语言。(ps:当时公司网络不连外网,而我也没有上网查资料的习惯,甚至那时候对电脑操作都不熟练...泪目)


师傅还是心地很善良很单纯的人,他隔一段时间会检查我的学习进度,然而当他激情澎拜给我讲着代码时,我竟控制不住打起了瞌睡,然后他就不管我了~~此后我便成了部门透明人物,要是一直透明下去就好了。我懒散的工作态度引起了部门主管的关注,于是我成了他重点关注的对象,我的工位更是移到了他身后~~这便是我的噩梦,一不小心神游时,主管的脸不知啥时凑到了我的电脑屏幕上~~~😱


偶然发现我的师傅在学习 php+html+css+js,他打算给部门构建一个网站,传统的脚本语言还是太简陋了。我在网上翻到了 w3scool离线文档 ,这一下子打开了我的 代码人生。后面我的师傅跳槽了,我在厂里呆了两年觉得什么都没学到,也考虑跳槽了。


后面的经历也很魔幻,误打误撞成为了一名前端开发工程师。此时是2018年,算是前端的鼎盛之年吧,各种新框架 vue/react/angular 都火起来了,各种网站/手机端应用如雨后春笋。我的前端之路还算顺利吧,下面讲讲我的经验吧


如何入门


对于外行转码农还是有一定成本的,省心的方式就是报班吧,但是个人觉得不省钱呀。培训班快则3个月,多的几年,不仅要交上万的培训费用,这段时间0收入,对于家境一般的同学,个人不建议报班。


但是现在市场环境不好,企业对你的容忍度不像之前那么高。之前几年行业缺人,身边很多只懂皮毛的人都可以进入,很多人在岗位半年也只能写出简单的页面,逻辑复杂一点就搞不定~~即使被裁了,也可以快速找到下家。这样的日子应该一去不复返了,所以我们还是要具备的实力,企业不是做慈善的,我们入职后还是要对的起自己的一份工资。


讲讲具体怎么入门吧


看视频:


b站上有很多很多免费的视频,空闲之余少刷点段子,去看看这些视频。不要问我看哪个,点击量大的就进去看看,看看过来人的经验,看看对这个行业的介绍。提高你的信息量,普通人的差距最大就在信息量的多少


还是看视频:


找一个系统的课程,系统的学习 html+css+js+vue/react,我们要动手写一些demo出来


做笔记:


对于新人来说,就是看了视频感觉自己会了,但是写起来很是费力。为啥呢?因为你不知道也记不住有哪些api,所以我们在看视频学习中,有不知道的语法就记下来。

我之前的经验就是手动抄写,最初几年抄了8个笔记本,但是后面觉得不是很方便,因为笔记没有归纳,后续整理笔记困难,所以我们完全可以用电子档的形式,这方便后面的归纳修改。我更多是将它当成一个手册吧,我自己也经常遗忘一些API,所以时不时会去翻翻。


回顾:


我们的笔记做了就要经常的翻阅,温故而知新,经常翻阅我们的笔记,经常去总结,突然有一天你的思维就上升了一个高度。



  • 慢慢你发现写代码就是不停调用api的过程

  • 慢慢你会发现程序里的美感,一个设计模式、一种新思维。我身边很多人都曾经深深沉迷过写代码,那种成就感带来的心流,这是物质享受带来不了的


输出:


就是写文章啦,写文章让我们总结回顾知识点,发现知识的盲区,在这个过程中进行了深度思考。更重要的是,对于不严谨的同学来说,研究一个知识点很容易浅尝则止,写文章驱动自己去更深层系统挖掘。不管对于刚入行的还是资深人士,我觉得输出都是很重要的。


持续提升


先谈谈学历歧视吧,现在很多大厂招聘基本条件就是211、985,对此很是无奈,但是我内心还是认可这种要求的,我对身边的本科985是由衷的佩服的。我觉得他们高考能考上985,身上都是有过人之处的,学习能力差不了。


见过很多工作多年的程序员,但是他们的编码能力无法描述,不管是逻辑能力、代码习惯、责任感都是很差的,写代码完全是应付式的,他们开发的代码如同屎山。额,但是我们也不要一味贬低他人,后面我也学会了尊重每一个人,每个人擅长的东西不一样,他可能不擅长写代码,但是可能他乐观的心态是很多人不及的、可能他十分擅长交际...


但是可能的话,我们还是要不断提高代码素养



  • 广度:我们实践中,很多场景没遇到,但是我们要提前去了解,不要等需要用、出了问题才去研究。我们要具备一定的知识面覆盖,机会是给有准备的人的。

  • 深度:对于现在面试动不动问源码的情况,很多人是深恶痛绝的,曾经我也是,但是当我沉下心去研究的时候,才发现这是有道理的。阅读源码不仅挺高知识的广度,更多让我们了解代码的美感


具体咋做呢,我觉得几下几点吧。(ps:我自己也做的不好,道理都懂,很难做到优秀呀~~~)



  • 扩展广度:抽空多看看别人的文章,留意行业前沿技术。对于我们前端同学,我觉得对整个web开发的架构都要了解,后端同学的mvc/高并发/数据库调优啥的,运维同学的服务器/容器/流水线啥的都要有一定的了解,这样可以方便的与他们协作

  • 提升深度:首先半路出家的同学,前几年不要松懈,计算机相关知识《操作系统》《计算机网络》《计算机组成原理》《数据结构》《编译原理》还是要恶补一下,这是最基础的。然后我们列出自己想要深入研究的知识点,比如vue/react源码、编译器、低代码、前端调试啥啥的,然后就沉下心去研究吧。


职业规划


现在整个大环境不好了,程序员行业亦是如此,身边很多人曾经的模式就是不停的卷,卷去大厂,跳一跳年薪涨50%不是梦,然而现在不同了。寒风凌凌,大家只想保住自己的饭碗(ps:不同层次情况不同呀,很多大厂的同学身边的同事还是整天打了鸡血一般)


曾经我满心只有工作,不停的卷,背面经刷算法。22年下半年市场明显冷下来,大厂面试机会都没有了,年过30,对大厂的执念慢慢放下。


我慢慢承认并接受了自己的平庸,然后慢慢意识到,工作只是生活的一部分。不一定要担任ceo,才算走上人生巅峰。最近几年,我爱上了读书,以前只觉得学理工科还是实用的,后面慢慢发现每个行业有它的美感~


最后引用最近的读书笔记结尾吧,大家好好体会一下论语的“知天命”一词,想通了就不容易焦虑了~~~



自由就是 坦然面对生活,看清了世界的真相依然热爱生活。宠辱不惊,闲看庭前花开花落。去留无意,漫随天外云卷云舒。



image.png




作者:chengliu0508
来源:juejin.cn/post/7343138429860347945
收起阅读 »

电话背调,我给他打了8分

前段时间招聘的一位开发,待了两三周,拿到了京东的offer,离职了。在离职的后一天,接到了他新公司的背调电话,几乎每项都给他打了8分。这个分数打的有点虚,单纯只是为了不影响他下家的入职。 离职之前,收到他在飞书上查看电话号码的消息,大概也猜到是在填写背调人信息...
继续阅读 »

前段时间招聘的一位开发,待了两三周,拿到了京东的offer,离职了。在离职的后一天,接到了他新公司的背调电话,几乎每项都给他打了8分。这个分数打的有点虚,单纯只是为了不影响他下家的入职。


离职之前,收到他在飞书上查看电话号码的消息,大概也猜到是在填写背调人信息,但自始至终,他也没打一声招呼,让给个好评。


离职最后一天,办完手续,没跟任何人打一个招呼,不知什么时候就消失了。


当初他刚入职一周时,其实大家都已经看出他在沟通上有很大问题,还想着如何对他有针对性的安排工作和调整,发挥他的长处,避免他的短处。但没想到这么快就离职了。在他提离职时,虽没过多挽留,但给了一些过来人的建议,很明显也听不进去。


站在旁观者的角度来看,他的职业生涯或即将面临到的事几乎能看得清清楚楚,但他有自己的坚持,别人是没办法的。


就着这事,聊聊最近对职场上关于沟通的一些思考:


第一,忌固执己见


职场中最怕遇到的一种人就是固执己见的人。大多数聪明人,在遇到固执己见的人时,基本上都会在三言两语之后停止与其争辩。因为,人一旦在自己的思维层次形成思维闭环,是很难被说服的。


而对于固执己见的人,失去的是新的思维、新的思想、纠错学习的机会,甚至是贵人的相助。试想一下,本来别人好像给你提建议,指出一条更好的路,结果换来的是争辩,是抬杠,聪明人都会敬而远之,然后默默地在旁边看着你掉坑里。


真正牛的人,基本上都是兼听则明,在获得各类信息、建议之后,综合分析,为己所用。


第二,不必说服,尊重就好


站在另外一个方面,如果一件事与己无关,别人有不同的意见,或者这事本身就是别人负责,那么尊重就好,不必强行说服对方,不必表现自己。


曾看到两个都很有想法的人,为一件事争论好几天,谁也无法说服谁。一方想用权力压另一方,另一方也不care,把简单的事情激化,急赤白脸的。


其实争论的核心只是展现形式不同而已,最终只是在争情绪、争控制感、争存在感而已,大可不必。


对于成年人,想说服谁都非常难的。而工作中的事,本身就没有对错,只有优劣,大多数时候试一下就知道了。


有句话说的非常好,“成年人的世界只做筛选,不做教育”。如果说还能做点什么,那就是潜移默化的影响别人而已。


第三,不懂的领域多听少说


如果自己对一个领域不懂,最好少发表意见,多虚心学习、请教即可。任正非辞退写《万言书》的员工的底层逻辑就是这个,不懂,不了解情况,还草率提建议,只是哗众取宠、浪费别人时间。


如果你不懂一个领域,没有丰富的背景知识和基础理论支撑,在与别人沟通的过程中,强行提建议,不仅露怯,还会惹人烦。即便是懂,也需要先听听别人的看法和视角解读。


站在另一个角度,如果一个不懂的人来挑战你的权威,质疑你的决定,笑一笑就好,不必与其争辩。


郭德纲的一段相声说的好:如果你跟火箭专家说,发射火箭得先抱一捆柴,然后用打火机把柴点着,发射火箭。如果火箭专家看你一眼,就算他输。


第四,没事多夸夸别人


在新公司,学到的最牛的一招就是夸人。之前大略知道夸人的效果,但没有太多的去实践。而在新公司,团队中的几个大佬,身体力行的在夸人。


当你完成一件事时,夸“XXX,真牛逼!”,当你解决一个问题时,夸“还得是XXX,不亏是这块的专家”。总之,每当别人有好的表现时,总是伴随着夸赞和正面响应。于是整个团队的氛围就非常好。


这事本身也不需要花费什么成本,就是随口一句话的事,而效果却非常棒。与懂得“人捧人,互相成就彼此,和气生财”的人相处,是一种非常愉悦的体验。


前两天看到一条视频,一位六七岁的小姑娘指派正在玩游戏的父亲去做饭,父亲答应了。她妈妈问:你是怎么做到的?她说:夸他呀。


看看,这么小的小孩儿都深谙的人性,我们很多成人却不懂,或不愿。曾经以为开玩笑很好,现在发现“夸”才是利器,同时一定不要开贬低性的玩笑。


其实,职场中还有很多基本的沟通规则,比如:分清无效沟通并且及时终止谈话、适当示弱、认真倾听,积极反馈、少用反问等等。


当你留意和思考这些成型的规则时,你会发现它们都是基于社会学和心理学的外在呈现。很有意思,也很有用。


作者:程序新视界
来源:juejin.cn/post/7265978883123298363
收起阅读 »

你的年终奖怎么算个税?你的算法对吗?

又到了一年一度的报税阶段。相信现在很多人都是把年终奖分出来单独计税的,但是最近在计算年终奖交税的时候,突然觉得有些怪怪的,网上一查,不止我一个人发现有问题,这里记录一下,也听听大伙有什么看法。 前置工作,我们先来看看个税是怎么计算的。 单独计算 应纳税额 = ...
继续阅读 »

又到了一年一度的报税阶段。相信现在很多人都是把年终奖分出来单独计税的,但是最近在计算年终奖交税的时候,突然觉得有些怪怪的,网上一查,不止我一个人发现有问题,这里记录一下,也听听大伙有什么看法。


前置工作,我们先来看看个税是怎么计算的。


单独计算


应纳税额 = 年终奖金额 × 适用税率 - 速算扣除数



出处:财政部税务总局公告2023年第30号,自己百度



假设我拿了 40000 年终奖,而且设置单独计算,按照 2023 年税法规定,年终奖适用的七档分阶段税率以及速算扣除数如下(税表三):



全年一次性奖金单独计税的优惠政策曾在2021年12月延续2年,原本将于2023年年底到期。23年发布的《关于延续实施全年一次性奖金个人所得税政策的公告》将该政策再延4年



image.png



来源:http://www.gerensuodeshui.cn/index_gsslb…



适用税率使用的是年终奖总额除以12,分摊到12个月里的均值:40000 / 12 = 3333.33..., 查表后显示我在第 2 档,速算扣除数是 210,税率 10%.


按照计算公式,我的应交税额是:40000 * 10% - 210 = 3790.


合并计算


综合所得应纳税额 = {累计综合所得收入(含全年一次性奖金)-累计减除费用-累计专项扣除-累计专项附加扣除-累计依法确定的其他扣除-捐赠} × 适用税率-速算扣除数


顾名思义,就是将年终奖并入工资计算,这就适合税率表一了:


image.png


比如你每月工资 10000,允许扣除的三险一金每月为 2000 元,专项附加每月扣除 2000 元。并入以后全年收入所得:10000 * 12 + 40000 = 160000,查表可得在第三档。税率 20%:(160000 - 2000×12 - 2000×12)* 20% - 16920 = 5480.


交的税明显多多了,你会想,只有傻子才会合并计算啊!


单独 or 合并 ?


但是也有例外,比如你一个工资 5000,年终奖 500000,允许扣除的三险一金每月为 2000 元,专项附加每月扣除2000元,没有其他扣除项目。则单独计税时,年终奖缴纳:500000 * 30% - 4410 = 145590,若是合并计算(全年 56w 收入,在表一的第五档)需缴纳:560000 - 2000 × 12 - 2000 × 12)× 30% - 52920 = 100680,这时候合并计算反而划算了。


大多数情况,当你工资比较多,年终奖相对较少时选择单独计算会更好;当你的年终奖在全年收入中占大头时,合并计算更有利。


临界点问题


你以为这就完了?问题才刚开始,看一下知乎有人的帖子:为什么年终奖个税会存在BUG?


讲的是在现行的税法和相关文件中,年终奖(全年一次性奖金)的个人所得税存在人为设计的「临界点问题」。这个问题新华网也证实了:新华网关于税费计算,即:高收入者的税后收入反而会比低收入者的税后收入还要低的问题


我们以单独计算为例,假设我年终奖拿了 36000,那么交税:36000 * 3% - 0 = 1080,那么我到手 34920. 假设老板发了善心,给我长了一块的工资,现在是 36001,那么查表可得,在表三中我跨档了,要交税:36001 * 10% - 210 = 3390.1, 此时我到手:32610.9,反而到手还低了!?


网上说是计算公式”弄错“了速算扣除数。速算扣除数并非税法规定,而是根据税法推算出来的一个方便计算的系数。至于速算扣除数怎么来的,可以看这篇知乎文章,写的很详细。我这里总结一下,就是速算扣除数是反推计算的:



  • 税率3%对应速算扣除数为0

  • 税率10%对应速算扣除数为3000*(10%-3%)+0=210

  • 税率20%对应速算扣除数为12000*(20%-10%)+210=1410

  • 税率35%对应速算扣除数为25000*(25%-20%)+555=2660

  • ...


按我们这个例子:


36,000元,除以12得3000.0000,对应税率3%,速算扣除数0,


税金: 1080 元;


36,001元,除以12得3000.0833,对应税率10%,速算扣除数210,


税金: 1590.1;


据那篇文章所说,问题出现在速算扣除数上,这里的速算扣除数应该用年的,而公式只用了月的


如果你还是不清楚,我们不用速算扣除数计算,我们按照税法规定的:



  • 不超过1500元的 3

  • 超过1500元至4500元的部分 10

  • 超过4500元至9000元的部分 20

  • 超过9000元至35000元的部分 25

  • ...


按照税法规定,36,000 年终奖,月平均是 3000,按照他“修订”的公式,应该缴纳:(3000 * 3% + 0 * 10%) * 12 = 1080,36,001 年终奖,月平均 3000.0833, 按照他“修订”的公式,应该缴纳:(3000 * 3% + 0.0833 * 10%) * 12 = 1080.1,等价于现行算法 (3000.0833 * 10% - 210) * 12 相对合理?


文章指出现行算法是这样的: 36001 * 10% - 210 = 3390.1。只减了一个210,就是说每个月都多算了 7%。


总结


按照推论,现有的速算扣除数 * 12 才是真正的速算扣除数。所以计算公式应该是:


应纳税额 = (年终奖金额 / 12 × 适用税率 - 速算扣除数) * 12


按照这个公式,上面36,000 年终奖,月平均是 3000,应该缴纳 (36000 / 12 * 3% - 0) * 12 = 1080,36,000 年终奖,月平均是 3000,应该缴纳 (36001 / 12 * 10% - 210) * 12 = 1080.1



依据: 财政部税务总局公告2023年第30号





所以,写到这里,我也糊涂了,年终奖交税到底要怎么算?谁能告诉我😓


作者:小肚肚肚肚肚哦
来源:juejin.cn/post/7346720393414492199
收起阅读 »