心静则神明。
心静则明,心诚则灵
老何的理解是:
内心若能平和冷静,才能临危不乱,从容淡定,才能有更高的境界和洞察力,遇事才能冷静思考分析,才能做出正确的判断和选择;
内心若能正心诚意,做到心无旁骛,专心致志,惟精惟一,锲而不舍,则必能获得灵验。或者说只要有坚定的信念,明确的目标,正确的心态和坚韧的毅力,心愿就一定会实现。
今天,老何在得到王立铭老师的《巡山报告》中看到对“心诚则灵”的最新生物学研究和解析,觉得很有意思。值得有兴趣的朋友学习和了解!
王立铭:“吃啥补啥”、“心诚则灵”和“针灸和穴位”的最新生物科学的研究及解释。
下文来源:得到 邵恒头条
作者:王立铭
你好,这里是《邵恒头条》,我是邵恒。
这周末,有“中国诺贝尔奖”之称的未来科学大奖,颁布了2020年的获奖名单。
跟以往一样,这次的奖项涵盖三个领域。一个领域是生命科学,此次获奖的,是在白血病领域开创了新治疗方法的两位科学家,张亭栋和王振义。
第二个领域是物质科学,此次获奖的是中科院的材料科学家卢柯,他在铜金属材料的研究上实现了突破。
还有一个领域是数学与计算机科学,这次获奖的是在数学金融领域作出过重大贡献的、山东大学的彭实戈教授。
我知道,这些领域对于我们普通人来说,可能显得很深奥,很陌生。但即便如此,我也注意到,今年我身边的朋友对这个奖项的关注度比以往更高。而且,我还注意到,这种关注其实还不限于这种高规格的科学奖项——不知道你有没有感受到,过去半年中,普通人对各种各样跟科学相关的新闻都格外地感兴趣。
这背后的原因可能是,疫情让很多人更真切地感受到,最前沿的科学进展跟我们每个人的生活密切相关。比如对于我来说,我最近就意识到,科学家做的很重要的一件事,就是把我们生活中的一些“谜题”转化为“问题”:谜题是那种完全没法解释的东西,你只能用“经验”、“直觉”甚至“迷信”来解释它。但“问题”就不一样了,它更像是一套拼图。你能用一套科学的方法,一步一步地拆解,直到最终找到答案。
在今天的《邵恒头条》中,我想跟你分享的是最新一期《巡山报告》,因为在这期报告里,王立铭老师用科学原理拆解了好几个有趣的生活谜题。有什么呢?比如吃啥补啥这件事靠不靠谱?是不是真的吃大枣补血,吃核桃补脑?
下面就一起来听听,第19期《巡山报告》。
你好,我是王立铭。2020年9月6日,第十九期《巡山报告》又和你见面了。
在刚刚过去的这个月,生命科学领域有三项非常有趣的研究,我认为你值得了解。有意思的是,这三项研究针对的都是一些充满争议的问题。
“吃啥补啥”有了新解释
只要是中国人,大概都或多或少受到过“食疗“这个概念的影响,也就是通过饮食调节身体状态、治疗疾病。特别是所谓的“吃啥补啥”“以形补形”的理念,比如吃红色的大枣补血、喝骨头汤补钙、吃核桃补脑等说法,我想你一定听说过不少。
但与此同时,这些说法也是许多科普文章的重点批评对象。毕竟在现代生物学的范畴里,不管吃了什么食物,都要被人体消化系统研磨、破坏、消化分解成非常简单的化学物质,比如葡萄糖、氨基酸、微量元素等,才能被人体吸收利用。不管核桃长得多像人脑、猪骨头和人骨头长得多像,吃下肚子一路消化分解,最后都是一堆生物体需要的最基本的原材料。按照这个理解,吃啥补啥、以形补形从逻辑上就是不可能的。
但是一直以来,生物研究圈子里有一个特立独行的案例给正反双方都出了一个难题——
南京大学生命科学学院的张辰宇教授,在过去十年里一直在关注这么一个问题:食物里有一类叫作“微小RNA”(microRNA)的化学物质,好像可以躲避被彻底分解的命运,直接被人体吸收,从而调节人体基因的活动,甚至改变人体正常的生理功能。
微小RNA这一类分子其实在复杂生物体内非常丰富,人体就能自己生产超过2000种不同的微小RNA分子。这类分子结构很简单,就是长度在20个碱基左右的一条核糖核酸片段。
我们知道,人体的RNA分子主要用来指导蛋白质生产。而微小RNA分子的长度太短,不能直接生产蛋白质,但可以通过一些复杂的生物学过程,干扰其他RNA分子的作用,影响蛋白质生产的效率。当然,这些说的都是同一个生物个体,一个生物自己生产出来的微小RNA分子,能影响自己生产蛋白质的效率,本质上是生命体内部的自我调节机制。
但是在2012年,张辰宇实验室发表了一篇在日后引起了巨大争议的论文。他们声称,稻米里含量丰富的几个微小RNA分子,特别是一个叫MIR168a的分子,在人体里竟然也相当丰富。看起来,它们可以通过消化系统进入血液和人体器官,甚至还可以调节人体一个叫作LDLRAP1的基因的活性,影响人体的血脂水平 [1]。
换句话说,张辰宇他们发现了一个物种之间的远距离调节机制——大米饭当中的微小RNA竟然能够直接进入人体,影响人体的基因活动。
从逻辑上说,如果张辰宇的研究属实,那食物提供给人体的就不光是简单的营养物质了,还有足以影响人体运行的生物学信息。这样的话,食物和人体的关系就变得非常复杂了。
比如,是不是吃啥补啥、以形补形还真可能有那么一点生物学依据?是不是人吃了什么食物,就会受到这些食物当中特殊的微小RNA分子的影响,所以人和人之间、人群和人群之间的差异可能是吃的东西不同导致的?还有,是不是转基因食品就更加危险?毕竟那里头除了天然的微小RNA,可能还有人工形成的微小RNA在发挥无法预测的作用[2]……
这个非常反直觉甚至有点耸人听闻的研究马上引起了各种争议和挑战。从技术上说,RNA分子是一类特别脆弱的化学物质,很多人压根不相信大米里的微小RNA居然能在蒸米饭的过程中保持完整,还能一路穿越人体消化道被完整吸收。也有人质疑,张辰宇他们在人体内检测到的大米的微小RNA,可能是试验样品被污染的结果。
平心而论,我自己曾经对这些发现也是充满怀疑的。毕竟生物学的主流认知一直都是,食物会被彻底分解破碎,然后以最简单的形态被人体吸收利用;毕竟食物里的微小RNA能直接干扰人体功能,也基本只是张辰宇实验室的一家之言。要知道,科学界一个不成文的规则就是——非同寻常的声明,需要非比寻常的证据支持。
面对这些质疑,在过去的十年里,张辰宇实验室一直在持续进行这方面的研究。2020年8月17日,他们在《细胞研究》杂志发表了一篇新论文,为我们接近真相提供了非常重要的线索 [3]。
在这篇论文里,张辰宇实验室发现,动物体内一个名叫SIDT1的蛋白质,看起来专门负责将微小RNA分子从细胞外运输到细胞内。而在小鼠胃黏膜细胞的细胞膜上,这个SIDT1蛋白质含量很丰富。更重要的是,删除小鼠体内这个SIDT1基因之后,研究者确实发现,小鼠对食物中微小RNA的吸收效率大大降低。从这些现象出发,他们提出了一个猜测——食物中的微小RNA分子,可能就是在胃部被吸收然后进入人体发挥功能的。
这项研究为什么重要呢?
因为在此之前,我们充其量只是有一些对现象的观察和描述,比如吃了大米饭之后,人体或者动物体内出现了一些本来只应该出现在大米当中的微小RNA。哪怕是张辰宇本人,大概也无法解释这个现象到底是怎么出现的。但现在我们知道,如果没有SIDT1,动物就没法吸收和利用食物中的微小RNA分子。这反过来可能就说明,在正常情况下,食物当中的微小RNA分子确实是可以进入动物体内的,而这个过程需要SIDT1。
在问题仅仅停留在观察和描述的时候,争论双方往往会陷入自说自话的僵局。你说你在人体内找到了大米的微小RNA,他说他做了一样的实验什么都没看到,我作为吃瓜群众不知道该信谁。就算我自己做了一遍实验,如果没有重复出张辰宇的发现,我也不知道是不是我的实验操作哪里做得不对。但是,发现了SIDT1这个蛋白质之后,科学家就可以直接去验证和拓展张辰宇的发现了。
比如,我可以去研究一下SIDT1这个蛋白质,看看它是不是真的可以运输微小RNA分子、是怎么运输的;你可以去看看如果人体缺乏SIDT1,是不是就不会吸收微小RNA了;他也可以看看别的食物当中,有没有什么其他的微小RNA分子也能通过SIDT1运输……这个充满争议的领域,第一次拥有了一个能够被第三方快速检验、从而一锤定音下结论的机会。
当然,我还是得强调一下,对于食物里的微小RNA是不是真的能进入人体、干扰人体功能,我其实还是将信将疑的。还是那句话,非同寻常的声明,需要非比寻常的证据。我们常说“孤证不立“,来自第三方实验室的重复和证明是必不可少的。
不过我们倒是不妨先畅想一下,如果这个理论真的得到证实,那意味着什么呢?
至少我们可以说,地球生物之间的关系远比我们曾经认知的复杂。就说一条简单的食物链吧——羊吃草,人吃羊,人死了之后尸体分解又被草吸收利用。传统上认为,在这个过程里,物种之间传递的无非就是各种化学物质和能量罢了。
但是换一个全新的视角,通过微小RNA分子,甚至可能还有别的化学物质,物种之间其实还在传递更加精细和丰富的生物学信息,甚至可以说,物种之间在直接对话。羊吃草的时候,草里的微小RNA可能会直接干预羊的生活;人吃羊的时候,羊肉里的微小RNA可能会干预人体的活动;人死之后,可能我们体内的微小RNA还会影响泥土里微生物和植物的状态。
如果这一切得到证实,地球生态系统还真的可以看作一个有机的整体,而人和环境的关系也远远不只是索取和利用那么简单。也许从某种意义上说,人类的世界观都会因此重塑。
当然,在畅想这一切之前,我们还是先耐心等待来自更多实验室的进一步研究吧。
“心诚则灵”的客观证据
说完“吃啥补啥“,咱们再聊聊第二项研究,它要回答的问题其实也挺魔幻的——心诚则灵到底存在不存在?
和吃啥补啥一样,心诚则灵也是一个被很多人挂在嘴边,但又不被现代科学和逻辑体系接受的说法。道理很简单,这个说法本质上可能就无法证伪。一个人到底心诚不诚,外人好像根本没有办法客观判断。比如考试之前去拜拜菩萨,考好了可以解释成菩萨显灵,考得不好可以说你烧香的时候不够虔诚。反正怎么说都有理。
既然怎么说都有理,那合理的态度就是敬而远之,不跟你打口水仗。不过,在生命科学领域,还真有一个和心诚则灵有关的严肃问题,是不能随便绕过去的。
它就是所谓的“安慰剂效应”。
你可能听过这个概念。它说的是,在很多时候,哪怕给一个病人用的是只有淀粉或者生理盐水这样的“假药”,只要这个人以为自己用的是真药,就能起到缓解病症的效果。因为这个原因,开发新药、做人体临床试验的时候,一般都需要一个步骤,就是开展随机对照的双盲试验——让两组病人分别使用真药和安慰剂假药,但不告诉他们自己用的到底是真药还是假药,然后再对比两组患者的病情变化。这种方式能有效排除安慰剂效应的干扰,确认一种新药到底有没有用、有多大用。
安慰剂效应的生物学本质至今还不是特别清楚,但我们必须正视它的存在。因为在某些时候,特别是针对像疼痛、抑郁症、失眠这类神经系统疾病的时候,安慰剂效应的强度已经大到了无法忽视,甚至可以和很多真药相提并论的程度。
安慰剂效应已经很神奇了吧?但接下来的事情可能会让你觉得更加不可思议。
在某些特定的疾病中,哪怕你直接告诉患者给他用的是没有药物成分的安慰剂,只要你同时告诉他安慰剂效应的存在,竟然也能起到缓解病情的效果。这就是所谓“非欺骗性安慰剂”的概念。
你看,这种现象是不是特别像心诚则灵?有个东西,哪怕明知道是假的,只要你选择相信,它就能有用。
当然,两者的区别是,心诚则灵是个无法证伪的说法,而非欺骗性安慰剂到底是怎么回事,我们还是有机会研究清楚的。
想要确认非欺骗性安慰剂的作用,一个传统思路是直接询问患者的感受。打个比方,研究者们可以给患者用非欺骗性安慰剂,比如淀粉做的药片,过一阵子问患者感觉是不是好点了。这样的研究其实做过不少,确实发现有不少疾病、不少患者哪怕明知道用了假药,也会觉得自己好转了。
但是,这类研究的一个大问题在于,我们不知道患者说自己好转了的时候,他是不是真的好转了。毕竟人是复杂的智慧生物,我们怎么知道这些患者不是怕研究者们失望而故意迎合?不是病情本身就在慢慢好转?或者人的大脑实在太善于脑补,以至于这些患者虽然病痛依旧,但是自己骗自己好转了,以至于自己都信了?
换句话说,我们缺少一个不依赖于患者主观描述的客观指标,来证明非欺骗性安慰剂效应是真实存在的。
2020年7月29日,来自美国密歇根大学等机构的研究者在《自然-通讯》杂志发表了一篇论文,第一次用客观证据证明了非欺骗性安慰剂效应的存在。心诚还真就能灵 [4]。
研究者的实验设计其实挺简单的:
他们找一群大学生作为受试者,让他们看电脑屏幕上随机出现的图片。有些是不带感情色彩的图片,比如一个皮球、一栋建筑;有些则是带有强烈负面刺激的图片,比如一个怪物头像、一个血淋淋的伤口、一个灾难现场等。然后,让学生们给自己的情绪打分,感觉越不舒服,分数就打得越高。这是一个主观指标。同时,他们还给学生们做了一个脑电图的记录,测量他们被强烈情绪刺激所激发的脑电波信号(晚期正电位,Late Positive Potential)。这是一个反映情绪的客观指标。
总体来说他们发现,看了那些惊悚可怕的图片之后,不管是主观还是客观指标,这群受试者的情绪状态都发生了明显的波动。这个不奇怪。
怎么验证非欺骗性安慰剂的作用呢?研究者是这么做的:
在实验开始前,研究者们会往每位受试者的鼻子里都喷点生理盐水,就是过敏性鼻炎患者经常用的那种喷雾。区别在于,对于其中一半的受试者,研究者们仅仅告诉他们鼻子里喷盐水是试验必需的常规操作;而对于另外一半受试者,科学家们明确告诉他们,我给你喷的是盐水没错,但是请把它当成安慰剂,你只要相信,它就能让你等会儿情绪不那么难受。就这么一点差别。
结果发现,不管是主观的情绪状态打分,还是客观的脑电波指标的测量,后面这一组学生的情绪状态都变好了。也就是说,这些学生明知道自己就是用了点生理盐水,但是只要他相信这东西管用,甚至只要他听说了这东西可能会有用,就真的会有用。非欺骗性安慰剂的效果第一次得到了实打实的证明。
这当然是个非常开脑洞的发现。我想,它的价值并不是结束了一个问题,而是开启了更多的问题。
比如,从脑科学的角度发问,这种明知道一个东西是假的但仍然会对它产生积极反应的现象,背后的原理是什么?是人脑的某种本能反应,还是人类特有的理性思维的结果?人和人之间、文化和文化之间、不同年龄的人之间,这种现象会不会有强弱之别?会不会有些人特别容易心诚则灵,而有些人天然对此免疫?这些人之间的差别又是怎么来的?是先天遗传,还是后天学习?
还有,从医学的角度来说,安慰剂效应,特别是非欺骗性安慰剂效应的客观存在,其实有正反两方面的作用。
从不好的地方说,这种效应让我们很难判断一种药物的真实效果到底如何,一定要借助随机对照双盲实验才能排除安慰剂效应。这本身就是一件费时费力、投入巨大的事,当然会提高新药开发的成本。甚至近年来还有一些研究发现,安慰剂效应好像有越来越强的趋势。换句话说,新药开发的门槛也因此越来越高了。
但是从好的地方来说,既然安慰剂效应真的存在,那么如果能想个办法利用它来缓解病痛,当然就是一个成本很低、安全性很高的办法。说得直白一点,对于那些吃一片淀粉药片、喷一点生理盐水就能治的病,我们就不需要再去开发药物了对不对?而且,如果搞清楚了安慰剂效应的生物学本质,也许还能进一步强化它,让它更好地帮助我们治疗疾病。这当然是一个特别值得继续研究的方向。
针灸和穴位的生物学基础
我要讲的第三项研究,针对的也是一个挺玄乎,而且特别容易引起争吵的话题——中医。更具体地说,是中医当中的针灸。
虽然中医这个话题太大、争议太多,但是一直以来,很多人都在努力把它纳入现代科学体系。其中最重要的两个方向,一个是用化学手段分析中药,从传统中草药里提取单一的有效成分并开发成药物。其中包括青蒿素、麻黄碱等成功案例,咱们这里就不多讨论了。另一个就是对针灸的研究,特别是搞清楚在什么部位、什么时间、用多大强度的针刺,能起到什么效果,这种效果又是如何实现的。
2014年,一项发表在《自然-医学》杂志的研究,首次发现了针灸对于败血症的治疗作用。
败血症是一种人类世界里死亡率很高的疾病,往往由全身性的细菌感染引起。人体免疫系统没有能力及时清除细菌,导致全身各个器官严重的免疫反应,引发持续的高烧、肝脾肿大、神智涣散乃至死亡。研究者们在小鼠身上模拟了人类败血症后发现,在小鼠的足三里穴,也就是小鼠后腿膝关节下面4毫米处的一个特定位置,插入很细的电极并通电刺激,模拟针灸的效果,可以有效缓解小鼠的败血症症状,降低死亡率 [5]。
到了2016年,研究者们在人体当中也发现了类似的现象。用电针刺激人体迷走神经,能够有效降低身体的免疫反应,缓解类风湿关节炎的症状 [6]。
从某种程度上说,这些研究已经部分证明,针灸这门古老的技艺可能确实有一些临床价值。但是从根本上说,我们还不太清楚针灸到底是通过什么生物学过程发挥作用的。
在中医理论里,经络是运行气血、贯通人体五脏六腑的通道,而穴位则是经络上重要的节点。只有在特定的穴位下针,影响特定经络的运行规律,才能起到预想的作用。但是,现代生物学并没有找到所谓的经络、穴位这种东西到底有没有可靠的物质基础。既然不知道穴位到底是什么,在不同地方针灸到底有什么区别,也就成了一个悬而未决的问题。
2020年8月12日,美国哈佛大学的科学家在《神经元》杂志发表论文,部分的解释了针灸的作用基础,特别是通过两个不同穴位的比较,解释了为什么针灸不同穴位能起到不同的作用 [7]。
这项研究的设计非常复杂,这里我为你提炼一下精髓。简单来说,哈佛大学的马秋富实验室重点关注了两个穴位——位于小鼠后腿上的足三里和位于小鼠腹部的天枢穴。他们发现,用电针刺激天枢穴或者足三里,都能很好地减轻小鼠的败血症病情,把患病小鼠的死亡率降低2/3。
但是两个穴位对针灸的反应,却存在很微妙的区别。具体来说,刺激足三里只需要0.5mA的微弱电流,而且不管是小鼠得败血症之前预先刺激,还是得病之后再刺激,治疗疾病的效果都不错。相反,如果刺激天枢穴的话,就一定要3mA的高强度电流才管用,而且一定要发病前预先刺激,发病以后再刺激反而会让病情恶化。
换句话说,下针的部位、下针的强度和下针的时机,三者共同性决定了针灸的效果。而这些指标,本来就是针灸技艺里特别重要的。从这个角度说,这项研究虽然不能说是给传统针灸技艺背书,但至少说明传统针灸经验里的很多关注点可能还真是有现实意义的。
为什么会存在这些区别呢?
马秋富教授的团队对此做出了一些解释。他们证明,在不同的部位下针,激活的是不同的神经系统的组成部分。低强度刺激足三里,能够通过迷走神经系统刺激肾上腺分泌多巴胺等神经信号分子,起到降低炎症反应的作用;而高强度刺激天枢穴,则是通过刺激脾脏去甲肾上腺素的分泌来调节炎症反应。如果分别杀死这些神经细胞,针灸这两个穴位的作用就会消失。
换句话说,所谓的不同穴位,其实就是能够和不同的神经系统产生联系的身体位置。这样看来,传统医学里那么多的穴位、复杂的针灸手法,可能就是为了保证在合适的时机、合适的位置,对人体的神经系统进行合适强度的刺激。这应该是生物学家能对针灸做出的比较合理的解释了。
当然,传统医学主要是对经验的总结。既然是对经验的总结,里面一定是鱼龙混杂,因为古代医生很难判断什么经验是真正有效的、什么经验仅仅是偶然的巧合甚至是完全错误的。打个比方,一包草药煮好喝下去,或者一针扎下去,患者觉得舒服多了,很多时候医生们并不知道到底是草药或者针灸的作用,还是安慰剂效应,又或者患者的疾病本来就会慢慢好转。也正是因为这样,很多研究者一直努力用现代科学和医学的逻辑重新梳理和检验传统医学的经验,去粗取精,去伪存真。
就拿这项研究来说吧,对于我而言,一个特别重要的启发是该如何定义穴位。
传统医学的实践里,很多穴位的具体位置是挺模糊甚至存在争议的。比如足三里,大致位置在膝盖骨外侧下方凹陷往下约4指宽的地方。不同的患者、不同的医生,可能找到的足三里位置都有细微的差别。还有些穴位,甚至不同医书的记载都无法统一。既然是这样,我们有没有办法给穴位做出一套客观的定义标准呢?
拿足三里和天枢穴做例子吧。现在我们知道,这两个穴位能够激活不同的神经系统组分、降低炎症反应。可它们到底是怎么和不同的神经系统组分联系起来的?是不是因为这两个穴位的皮肤下面分布着很多特殊的神经末梢,能够传递特殊的神经信号?如果确实如此,穴位的位置是不是可以干脆根据这些神经末梢的分布来定义?做个CT扫描就能定位,不需要用类似几根手指宽这样的模糊描述了。
类似的,我们是不是还能发现一些新的穴位,也就是那些和特定神经系统有紧密联系的身体表面部位?还有,除了减少炎症反应,刺激穴位还有没有别的功效?这些功效背后的原理是什么?除了刺激神经系统,穴位还有没有别的作用机制……
你看,这就是这项研究让我兴奋的地方。就像屠呦呦根据传统医书的记载,从青蒿里提取出了疟疾特效药青蒿素一样,也许从这项研究开始,我们也将慢慢把传统的针灸技艺里的精华纳入现代化的系统中来。
好了,这就是本期我要介绍的三项研究。
上一篇: 基于共调控功能模块的方法识别 miRNA-miRNA 共调控网络
下一篇: ceRNA 调控机制简介
推荐阅读
-
[刷新] 如果字符串 ="软件",则子串数为37
-
杂事几则
-
35 岁实现财务*,腾讯程序员手握2300万提前退休?-1000万房产、1000万腾讯股票、加上300万的现金,一共2300万的财产。有网友算了一笔账,假设1000万的房产用于自住,剩下1300万资产按照平均税后20-50万不等进行计算,大约花上26-60年左右的时间才能赚到这笔钱。也就是说,普通人可能奋斗一辈子,才能赚到这笔钱。在很多人还在为中年危机而惶惶不可终日的时候,有的人的35岁,就已经安全着陆,试问哪个打工人不羡慕?但问题是有这样财富积累必然有像样的实力做靠山。没有人可以不劳而获。 看到这里,肯定有人说,那么对于普通人来说,卷可能真就成了唯一的出路。但是卷也有轻松的卷,“偷懒”的卷法,对于程序员而言,刨除掉一时无法改掉的开会传统占用的大部分时间,如何把有限的时间和精力放在真正重要的架构设计、需求设计上,而不是重复的造*,编码、改bug、手动测试。因此在科技改变生活的今天,学会使用AI工具成为程序员们的必备技能。 以全栈式全自动的软件开发工具飞算SoFlu软件机器人为例,作为全球首款面向微服务架构设计和最佳实践的软件机器人,SoFlu软件机器人改变了原来手工编码的作业模式,通过可视化拖拽方式以及参数配置就能实现等同于编写复杂代码的业务逻辑,在设计业务逻辑时就完成了微服务应用开发,做到“业务即图,图即代码”,实现“软件开发,十倍提效”。 而作为飞算SoFlu软件机器人的一个重要组成部分,FuncGPT(慧函数)支持所有类型函数创建。通过自然语言描述Java函数需求,实时生成高质量、高可读性的Java函数代码。生成代码可直接复制到IDEA,或一键导入Java全自动开发工具函数库。 FuncGPT(慧函数)具有五大核心能力: ● 自然语言:通过自然语言即可生成函数,降低软件开发门槛。 ● 秒级函数开发:全自动秒级开发函数,秒级完成,效率千倍提升。 ● 一站式函数开发应用:函数生成即可直接应用,效率、安全有保障。 ● 质量可靠:生成的函数代码符合业界规范、具备良好的可读性,符合最优解。 ● 灵活生成:可以根据开发人员的具体需求生成并支持调整和修改。 以“将文件流转换为File对象”这个需求为例,以下是FuncGPT(慧函数)秒级生成的代码: / 类名:FileConverter // 函数名:convertStreamToFile // 函数功能:将文件流转换为File对象 // POM依赖包:无 import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; public class FileConverter { /** * 将文件流转换为File对象 * @param inputStream 文件流 * @param filePath 文件路径 * @param fileName 文件名 * @return 转换后的File对象 * @throws IOException 如果发生I/O异常 */ public static File convertStreamToFile(InputStream inputStream, String filePath, String fileName) throws IOException { File file = new File(filePath + File.separator + fileName); // 创建File对象 try (FileOutputStream outputStream = new FileOutputStream(file)) { // 创建文件输出流 byte buffer = new byte[1024]; int bytesRead; while ((bytesRead = inputStream.read(buffer)) != -1) { // 从文件流读取数据并写入文件 outputStream.write(buffer, 0, bytesRead); } } return file; // 返回转换后的File对象 } } // 函数示例 // 将文件流转换为File对象示例 // 入参:inputStream,文件流 // 入参:filePath,文件路径 // 入参:fileName,文件名 // 出参:file,转换后的File对象 // 调用示例: // InputStream inputStream = new FileInputStream("example.txt"); // String filePath = "C:\\Users\\User\\Documents"; // String fileName = "example.txt"; // File file = FileConverter.convertStreamToFile(inputStream, filePath, fileName); // System.out.println(file.getAbsolutePath); // 输出结果:例如,将文件流转换为File对象后,文件的绝对路径为:C:\Users\User\Documents\example.txt // 则输出结果为:C:\Users\User\Documents\example.txt 通过分析,不难发现以上代码:
-
静则一念不生,动则万善随身。
-
微信 "扫一扫 "物联网,全面揭秘 "扫一扫 "背后的扫盲技术!-1.1 扫一扫感知物体是做什么的? 1.1 微信扫一扫是做什么的? 扫一扫识物是指以图片或视频(商品图片:鞋/包/美妆/服饰/家电/玩具/图书/食品/珠宝/家具/其他商品)为输入媒介,挖掘微信内容生态中的有价值信息(电商+百科+资讯,如图1所示),并展示给用户。这里的电商基本涵盖了微信小程序覆盖上亿SKU的全量优质电商,可以支持用户货比N家并直接下单购买,百科和资讯则聚合了微信内的头部自媒体如搜狗、搜搜、百度等,向用户展示和分享拍摄商品相关的内容资讯。 图 1 扫一扫识别功能示意图 欢迎大家更新iOS新版微信→扫一扫→识货,亲自体验,也欢迎大家通过识货界面的反馈按钮向我们提交反馈意见。 扫一扫识物实景图展示 1.2 扫一扫识物有哪些使用场景? 扫一扫识物的目的是为用户访问微信内部生态内容开辟一个新窗口,以用户扫图片为输入形式,为用户提供微信生态内容中的百科、资讯、电商等作为展示页面。除了用户熟悉的扫一扫操作外,我们还将进一步拓展长按操作,让用户更方便地进行扫一扫操作。"扫一扫知事 "的落地场景主要涵盖三大部分: a. 科普知识: a.科普知识。用户通过扫一扫,可以在微信生态圈中获取该对象的百科、资讯等常识或趣闻,帮助用户更好地了解该对象; b.购物场景。同样的搜索功能支持用户看到喜欢的商品立即检索到微信小程序电商中的同款商品,支持用户即扫即购; c.广告场景。扫一扫识别物体可以辅助公众号文章、视频更好地理解其中蕴含的图片信息,从而更好地投放匹配广告,提高点击率。 1.3 Sweep Sense 为 Sweep 家族带来了哪些新技术? 对于扫一扫来说,大家耳熟能详的应该就是扫一扫二维码、扫一扫小程序码、扫一扫条形码、扫一扫翻译了。无论是各种形式的编码还是文字字符,都可以看作是图片的一种特定编码形式,而物的识别则是对自然场景图片的识别,这对于扫一扫家族来说是一个质的飞跃,我们希望从物的识别入手,进一步拓展扫一扫对自然场景图片的理解能力,比如扫酒、扫车、扫植物、扫人脸等服务,如下图3所示。 图 3 Sweep 家族
-
Python 设置了体温检测程序,如果体温低于 37.3 度,则体温正常;如果体温高于或等于 37.3 度,则体温正常。
-
Spring 事务传播机制和事务挂起 - PROPAGATION_MANDATORY:支持(使用)当前事务,如果它不存在,则抛出异常
-
epoll简介及触发模式(accept、read、send)-epoll的简单介绍 epoll在LT和ET模式下的读写方式 一、epoll的接口非常简单,一共就三个函数:1. int epoll_create(int size);创建一个epoll的句柄,size用来告诉内核这个监听的数目一共有多大。这个参数不同于select中的第一个参数,给出最大监听的fd+1的值。需要注意的是,当创建好epoll句柄后,它就是会占用一个fd值,在linux下如果查看/proc/进程id/fd/,是能够看到这个fd的,所以在使用完epoll后,必须调用close关闭,否则可能导致fd被耗尽。2. int epoll_ctl(int epfd, int op, int fd, struct epoll_event *event);epoll的事件注册函数,它不同与select是在监听事件时告诉内核要监听什么类型的事件,而是在这里先注册要监听的事件类型。第一个参数是epoll_create的返回值,第二个参数表示动作,用三个宏来表示:EPOLL_CTL_ADD:注册新的fd到epfd中;EPOLL_CTL_MOD:修改已经注册的fd的监听事件;EPOLL_CTL_DEL:从epfd中删除一个fd;第三个参数是需要监听的fd,第四个参数是告诉内核需要监听什么事,struct epoll_event结构如下:struct epoll_event { __uint32_t events; /* Epoll events */ epoll_data_t data; /* User data variable */};events可以是以下几个宏的集合:EPOLLIN :表示对应的文件描述符可以读(包括对端SOCKET正常关闭); EPOLLIN事件:EPOLLIN事件则只有当对端有数据写入时才会触发,所以触发一次后需要不断读取所有数据直到读完EAGAIN为止。否则剩下的数据只有在下次对端有写入时才能一起取出来了。现在明白为什么说epoll必须要求异步socket了吧?如果同步socket,而且要求读完所有数据,那么最终就会在堵死在阻塞里。 EPOLLOUT:表示对应的文件描述符可以写; EPOLLOUT事件:EPOLLOUT事件只有在连接时触发一次,表示可写,其他时候想要触发,那要先准备好下面条件:1.某次write,写满了发送缓冲区,返回错误码为EAGAIN。2.对端读取了一些数据,又重新可写了,此时会触发EPOLLOUT。简单地说:EPOLLOUT事件只有在不可写到可写的转变时刻,才会触发一次,所以叫边缘触发,这叫法没错的!其实,如果真的想强制触发一次,也是有办法的,直接调用epoll_ctl重新设置一下event就可以了,event跟原来的设置一模一样都行(但必须包含EPOLLOUT),关键是重新设置,就会马上触发一次EPOLLOUT事件。1. 缓冲区由满变空.2.同时注册EPOLLIN | EPOLLOUT事件,也会触发一次EPOLLOUT事件这个两个也会触发EPOLLOUT事件 EPOLLPRI:表示对应的文件描述符有紧急的数据可读(这里应该表示有带外数据到来);EPOLLERR:表示对应的文件描述符发生错误;EPOLLHUP:表示对应的文件描述符被挂断;EPOLLET: 将EPOLL设为边缘触发(Edge Triggered)模式,这是相对于水平触发(Level Triggered)来说的。EPOLLONESHOT:只监听一次事件,当监听完这次事件之后,如果还需要继续监听这个socket的话,需要再次把这个socket加入到EPOLL队列里3. int epoll_wait(int epfd, struct epoll_event * events, int maxevents, int timeout);等待事件的产生,类似于select调用。参数events用来从内核得到事件的集合,maxevents告之内核这个events有多大,这个maxevents的值不能大于创建epoll_create时的size,参数timeout是超时时间(毫秒,0会立即返回,-1将不确定,也有说法说是永久阻塞)。该函数返回需要处理的事件数目,如返回0表示已超时。-------------------------------------------------------------------------------------------- 从man手册中,得到ET和LT的具体描述如下EPOLL事件有两种模型:Edge Triggered (ET)Level Triggered (LT)假如有这样一个例子:1. 我们已经把一个用来从管道中读取数据的文件句柄(RFD)添加到epoll描述符2. 这个时候从管道的另一端被写入了2KB的数据3. 调用epoll_wait(2),并且它会返回RFD,说明它已经准备好读取操作4. 然后我们读取了1KB的数据5. 调用epoll_wait(2)......Edge Triggered 工作模式:如果我们在第1步将RFD添加到epoll描述符的时候使用了EPOLLET标志,那么在第5步调用epoll_wait(2)之后将有可能会挂起,因为剩余的数据还存在于文件的输入缓冲区内,而且数据发出端还在等待一个针对已经发出数据的反馈信息。只有在监视的文件句柄上发生了某个事件的时候 ET 工作模式才会汇报事件。因此在第5步的时候,调用者可能会放弃等待仍在存在于文件输入缓冲区内的剩余数据。在上面的例子中,会有一个事件产生在RFD句柄上,因为在第2步执行了一个写操作,然后,事件将会在第3步被销毁。因为第4步的读取操作没有读空文件输入缓冲区内的数据,因此我们在第5步调用 epoll_wait(2)完成后,是否挂起是不确定的。epoll工作在ET模式的时候,必须使用非阻塞套接口,以避免由于一个文件句柄的阻塞读/阻塞写操作把处理多个文件描述符的任务饿死。最好以下面的方式调用ET模式的epoll接口,在后面会介绍避免可能的缺陷。 i 基于非阻塞文件句柄 ii 只有当read(2)或者write(2)返回EAGAIN时才需要挂起,等待。但这并不是说每次read时都需要循环读,直到读到产生一个EAGAIN才认为此次事件处理完成,当read返回的读到的数据长度小于请求的数据长度时,就可以确定此时缓冲中已没有数据了,也就可以认为此事读事件已处理完成。Level Triggered 工作模式相反的,以LT方式调用epoll接口的时候,它就相当于一个速度比较快的poll(2),并且无论后面的数据是否被使用,因此他们具有同样的职能。因为即使使用ET模式的epoll,在收到多个chunk的数据的时候仍然会产生多个事件。调用者可以设定EPOLLONESHOT标志,在 epoll_wait(2)收到事件后epoll会与事件关联的文件句柄从epoll描述符中禁止掉。因此当EPOLLONESHOT设定后,使用带有 EPOLL_CTL_MOD标志的epoll_ctl(2)处理文件句柄就成为调用者必须作的事情。然后详细解释ET, LT:LT(level triggered)是缺省的工作方式,并且同时支持block和no-block socket.在这种做法中,内核告诉你一个文件描述符是否就绪了,然后你可以对这个就绪的fd进行IO操作。如果你不作任何操作,内核还是会继续通知你的,所以,这种模式编程出错误可能性要小一点。传统的select/poll都是这种模型的代表.ET(edge-triggered)是高速工作方式,只支持no-block socket。在这种模式下,当描述符从未就绪变为就绪时,内核通过epoll告诉你。然后它会假设你知道文件描述符已经就绪,并且不会再为那个文件描述符发送更多的就绪通知,直到你做了某些操作导致那个文件描述符不再为就绪状态了(比如,你在发送,接收或者接收请求,或者发送接收的数据少于一定量时导致了一个EWOULDBLOCK 错误)。但是请注意,如果一直不对这个fd作IO操作(从而导致它再次变成未就绪),内核不会发送更多的通知(only once),不过在TCP协议中,ET模式的加速效用仍需要更多的benchmark确认(这句话不理解)。在许多测试中我们会看到如果没有大量的idle -connection或者dead-connection,epoll的效率并不会比select/poll高很多,但是当我们遇到大量的idle- connection(例如WAN环境中存在大量的慢速连接),就会发现epoll的效率大大高于select/poll。(未测试)另外,当使用epoll的ET模型来工作时,当产生了一个EPOLLIN事件后,读数据的时候需要考虑的是当recv返回的大小如果等于请求的大小,那么很有可能是缓冲区还有数据未读完,也意味着该次事件还没有处理完,所以还需要再次读取: 这里只是说明思路(参考《UNIX网络编程》) while(rs) {buflen = recv(activeevents[i].data.fd, buf, sizeof(buf), 0);if(buflen < 0){// 由于是非阻塞的模式,所以当errno为EAGAIN时,表示当前缓冲区已无数据可读// 在这里就当作是该次事件已处理处.if(errno == EAGAIN)break; else return; }else if(buflen == 0) { // 这里表示对端的socket已正常关闭. } if(buflen == sizeof(buf) rs = 1; // 需要再次读取 else rs = 0; } 还有,假如发送端流量大于接收端的流量(意思是epoll所在的程序读比转发的socket要快),由于是非阻塞的socket,那么send函数虽然返回,但实际缓冲区的数据并未真正发给接收端,这样不断的读和发,当缓冲区满后会产生EAGAIN错误(参考man send),同时,不理会这次请求发送的数据.所以,需要封装socket_send的函数用来处理这种情况,该函数会尽量将数据写完再返回,返回-1表示出错。在socket_send内部,当写缓冲已满(send返回-1,且errno为EAGAIN),那么会等待后再重试.这种方式并不很完美,在理论上可能会长时间的阻塞在socket_send内部,但暂没有更好的办法. ssize_t socket_send(int sockfd, const char* buffer, size_t buflen) { ssize_t tmp; size_t total = buflen; const char *p = buffer; while(1) { tmp = send(sockfd, p, total, 0); if(tmp < 0) { // 当send收到信号时,可以继续写,但这里返回-1. if(errno == EINTR) return -1; // 当socket是非阻塞时,如返回此错误,表示写缓冲队列已满, // 在这里做延时后再重试. if(errno == EAGAIN) { usleep(1000); continue; } return -1; } if((size_t)tmp == total) return buflen; total -= tmp; p += tmp; } return tmp; } 二、epoll在LT和ET模式下的读写方式 在一个非阻塞的socket上调用read/write函数, 返回EAGAIN或者EWOULDBLOCK(注: EAGAIN就是EWOULDBLOCK) 从字面上看, 意思是: * EAGAIN: 再试一次 * EWOULDBLOCK: 如果这是一个阻塞socket, 操作将被block * perror输出: Resource temporarily unavailable 总结: 这个错误表示资源暂时不够, 可能read时, 读缓冲区没有数据, 或者, write时,写缓冲区满了 。 遇到这种情况, 如果是阻塞socket, read/write就要阻塞掉。 而如果是非阻塞socket, read/write立即返回-1, 同 时errno设置为EAGAIN. 所以, 对于阻塞socket, read/write返回-1代表网络出错了. 但对于非阻塞socket, read/write返回-1不一定网络真的出错了. 可能是Resource temporarily unavailable. 这时你应该再试, 直到Resource available. 综上, 对于non-blocking的socket, 正确的读写操作为: 读: 忽略掉errno = EAGAIN的错误, 下次继续读 写: 忽略掉errno = EAGAIN的错误, 下次继续写 对于select和epoll的LT模式, 这种读写方式是没有问题的. 但对于epoll的ET模式, 这种方式还有漏洞. epoll的两种模式 LT 和 ET
-
5.1.3 边界值法--二元基本边界值分析 边界值测试的另一个关键假设是,故障很少是由两个(或两个以上)缺陷同时出现造成的,这在可靠性理论中称为 "单一缺陷 "假设。基于 "单一缺陷 "假设的边界值测试称为基本边界值分析。 在边界值测试中,我们通常使用两值边界,然后辅助以正常值来设计输入变量的值。 对于只有 x 和 y 两个输入变量的软件,输入域在二维坐标系中呈阴影状。使用基本边界值分析法得到的测试用例就是黑点所在的位置,总共有九个测试用例。 如果有一个 n 变量的软件输入域,则选择其中一个变量略小于最小值、最小值、正常值、最大值和略大于最大值这五个值,其余全部取正常值。对这个 n 个变量的软件输入域进行边界值分析,可产生 4n+1 个测试用例。 三值基本边界值分析
-
像首席技术官一样思考:如何高效管理 30 人的研发团队?-管理越多越轻松。好的研发团队,应该是上拨下用,即下级对上级的向上管理;而不是反过来,总是向下管理,甚至是 CTO 做经理的事,经理做工程师的事,工程师最终会被当成实习生。如果是这样,就会越管越累,不仅团队无法成长,而且团队整天很忙还效率低下,问题一大堆。 有这样一个小故事:一位高级经理下班后帮忙倒垃圾,结果被老板训斥了一顿。这就好比首席技术官做了实习生自己该做的事。事情本身没有对错之分,只是从不同的角度有不同的理解。 古人云:"用人不疑,疑人不用"。在面对自己的研发团队时,应该相信他们能做好,授权一线开发人员充分发挥专业特长,不要限制他们的工作。但在相信他们的同时,也要进行二次确认,始终秉持 "我相信,但我要确认 "的原则和严谨的精神。因为每个人都会犯错和疏忽,通过发挥团队的智慧,团队犯错的机会就会大大减少。比如回归测试、代码审查、开发演示、变更审批等等。 如前所述,每个人都难免会犯错。但作为管理者,你所设计和商定的流程不能出错。管理者的每一个决定和沟通都应该经过深思熟虑。就像红绿灯的交通设计,某辆车不小心闯红灯可能会扣分,但红绿灯的设计一定要正确、人性化、统一。再比如,开发人员可能会因为疏忽大意写出 bug,但研发流程的设计和上线流程的发布不能有任何差错。因此,流程体系的设计,一方面要结合当前团队规模、业务特点和需要重点解决的问题来设计,另一方面也要在人员防错、效率提升、发挥团队集体智慧等维度进行综合考量。应该站在更高更抽象的角度去思考,不断思考一个倍受欢迎的园区应该如何设计,思考一个灵动、经典、永恒的建筑应该遵循怎样的模式,思考一个成功、优秀、卓越的研发团队应该需要怎样的流程和制度。 最后,反馈很重要。向上汇报很重要,向下反馈也很重要。能够保持顺畅的双向反馈和闭环管理,对研发团队的协作和沟通有着非常明显的积极作用。在向上汇报方面,要培养团队在正式汇报、会议汇报、私下沟通、书面总结、非正式场合等方面的沟通能力,提醒下属报喜也要报忧。凡事先记录,再跟进,最后反馈。反馈很重要,主动汇报更难得。 另一方面,同时也不要忽视向下反馈。好的爱,是双向的。团队也是如此,没有严格的上下级之分,只是分工和角色不同而已。作为管理者,不必总保持一种 "神秘感",让人 "捉摸不透 "才是牛。当团队做得好或有人做得好时,要记得在公开或私下场合给予肯定和赞许。业务有增长、业绩有提升时,别忘了给团队一些鼓励,或者安排一次下午茶或聚餐。在例会或正式会议上,也可以同步向大家传达一些重要信息和高层指示。"欲速则不达,欲远则同行"。 当向上汇报、向下反馈的沟通闭环形成后,同时结合前面研发过程的管理闭环,双管齐下,就能形成良性循环。如此反复,持之以恒,优秀卓越的研发团队,必将呈现。 能力、产出和效率 接下来,继续重复关于能力、产出和效率的话题。 站在不同的角色,以及一个企业经营、生存和发展所需要的基础上,我把研发生产力分为三个层次,分别是:一线员工关心的研发能力、管理层关心的软件产出和操作人员关心的企业生产效率。简单概括就是:既要把工作做好,又要能出成果,还要能帮企业赚钱。