作者|Lenny Rachitsky
OneFlow编译
翻译|凌小雨、张雪聃
题图由SiliconCloud平台生成
作为一家刚成立不到两年的新公司,AI搜索新星Perplexity与搜索巨头Google和AI先锋OpenAI展开竞争,争夺未来搜索领域的一席之地。
目前,Perplexity已经拥有数以千万计的用户,不过,该团队的成员还不到50人。更令人振奋的是,这个年轻团队已经实现了超过2000万美元的年度经常性收入(ARR)。
最近,他们完成了一笔6300万美元的融资,公司估值超10亿美元,其投资者包括英伟达、亚马逊创始人Jeff Bezos、OpenAI创始成员Andrej Karpathy、知名投资人Garry Tan、Dylan Field、Elad Gil、Nat Friedman、Daniel Gross和Naval Ravikant。英伟达CEO黄仁勋曾公开表示,他几乎每天都在使用Perplexity。
知名博主Lenny Rachitsky近期与Perplexity联合创始人兼产品负责人Johnny Ho进行了一次对话,后者从内部视角深入介绍了Perplexity如何构建产品。
以下是部分要点摘要:
AI优先:员工们一直都在向AI询问有关公司构建过程步骤相关的问题,包括“如何推出产品?”公司鼓励员工在打扰同事之前先向AI提问;
组织灵活高效:通过将项目分解成多个并行任务来最大限度地减少团队间的协调成本;
小而精的团队:Perplexity的标准团队通常只有两到三名成员工,其AI生成(且评价极高)的播客仅由一个人创建、运营;
扁平化管理:Perplexity倾向于雇佣自我驱动力强的独立贡献者,并尽量避免招聘在团队中喜欢指挥别人干活的员工;
既懂技术又有产品见解的优秀产品经理/工程师:Johnny的大胆猜想是,随着时间的流逝,那些既懂技术又对产品有独到见解的产品经理或工程师,将成为公司最宝贵的资产。
(本文由OneFlow编译发布,转载请联系授权原文: https://www.lennysnewsletter.com/p/how-perplexity-builds-product)
1. Perplexity内部如何使用AI工具来构建Perplexity?
其实,一开始我们也是盲人摸象,对产品管理、项目管理、财务、人力资源等没有具体的认知。
幸运的是,我们有机会提前接触GPT-3,创立之初,我们总是先向AI求助,比如“X是什么?”“那我们该如何正确地完成它?”比如,我们会问:“如何发布产品?发布过程中的步骤是什么?”等问题。
AI会给我们一个大致的步骤流程,这对初创公司来说已经足够好。当然,第一次尝试往往都不尽如人意,但谁又能一开始就做到完美?所以我们在哪里摔倒就在哪里爬起来,不断试错、学习、迭代。
我们花了好几天尝试自己解决问题。但是有了AI的一点提示,我们可以在五分钟内就开始行动。
我们还在继续使用这样的方法。例如,本周我问Perplexity:“怎么写一封邀请别人试用Perplexity Pro的邮件?”
我们有时候甚至用AI工具来构建自己的产品,但发现在编程方面,AI工具还需要迭代。它可以帮我们编写脚本,但如果想在平台上构建可持续的代码就不太行了。
即使在今天,随着技术的进步和新模型的出现,这些工具也只能写写模板,没办法真正用它来设计那些能长久使用的抽象化技术。
2. 你们有多少产品经理?
在我们这个50人的团队里,只有两名全职产品经理。这两位产品经理负责的项目通常只有一两个人参与,最棘手的项目最多也只有三四个人。
比如,我们的播客就是由一个人一手包办的。他是品牌设计师,但同时也会做音频工程,并进行各种研究,以打造一个最具互动性和趣味性的播客。我认为,到目前为止,还没有产品经理介入过这个过程。
遇到非常困难且有多种选择的决策时,以及在更复杂的项目中,产品管理最能发挥其优势。
产品经理工作中最困难也是最重要的部分是对应用场景具有很好的判断力。在AI领域,可能存在的应用场景数量太多。因此,产品经理需要根据数据、用户研究等信息,做出分支定性决策。AI领域的一个重要问题是应该优先考虑以提高生产力为主的使用场景,还是聊天机器人类的互动性使用场景。很早以前,我们就决定专注于前者,但相关讨论仍在继续。
我们计划在未来一年内再招一到两位产品经理,但招聘标准不会降低。
3. 你们的成功很大程度上是因为招聘得当,并保持了非常高的标准。在招聘时,你们最看重的(但别人可能没注意到的)特质是什么?
鉴于我们工作的速度,我们首先会要求灵活性和主动性。在资源有限的环境中能够积极建设性地工作(可能要身兼数职)对我们来说最重要。
看产品经理的简历时,很多人会强调帮助他人、寻求共识的特质。但我认为,随着AI的出现,这一点将变得不那么重要,你不一定需要擅长管理流程或领导别人。我们更看重那些在用户群体中产生明确量化影响的强大的个体贡献者,而不是只在公司内部表现出色的人。如果简历中出现“敏捷专家”或“Scrum大师”这样的描述,这个人可能不太适合我们。
此外,AI让产品经理能做更多的技术工作,尤其是数据分析和客户洞察方面。当然,还是需要一些基本知识(例如对数学、统计学、编程的基本理解),但现在成为真正“技术型”的产品经理已经比从前用容易不少。
我们也很看重候选人与我们企业文化的契合度,易于合作很重要,我们不太想要那种擅长指导他人工作的人,在AI时代,这种人并不是很必要。也许,未来公司规模扩展之后,我们的需求会有所改变,但在目前的规模下,需要构建的产品数量远远多于投入这些工作的员工数量。
我认为,未来整个行业的管理层将会减少。随着时间推移,技术产品经理或有产品敏锐度的工程师将成为公司中最宝贵的人才。
4. 你们的团队以围绕产品、用户类型、用户旅程、成果,还是介于这些之间的某种方式来构建?这些年来,这种结构有没有发生变化?
我的目标是构建团队,力求减少所谓的“协调阻力”,正如Alex Komoroske把组织比作黏菌时所描述的那样。
我们的核心观点是,随着规模扩大,由不确定性和分歧引起的协调成本会随之上升,单纯增加管理层并不能解决问题。员工的动机可能会不一致,甚至可能出现上下级之间相互隐瞒的情况。如果你想和公司里其他部门的人沟通,可能得经过一层层的上传下达,要问遍所有人。
相反,我们可以保持总体目标一致,通过共享可复用的指导和流程,让项目并行推进,共同指向这个目标。特别是在AI的帮助下,我们可以用它实现“小黄鸭调试法”(当程序员在解释他们的代码时,就像对着一个橡皮鸭(rubber duck)说话一样。通过解释问题,程序员往往能在解释过程中自己发现问题所在,或者至少能更清晰地理解问题。)从而对我们的想法进行测试,而不必依赖于完美的对齐和共识,这样就能降低协调成本。我们还在内部文档中建立了一个“人物名录”,需要联系谁,直接就能联系。这需要很高的信任度。
更重要的是,有了AI,你不用再频繁地向他人求助。有时候,在向别人提问之前,你可以先尝试花一分钟让AI回答,以减少协调成本,这也能给每个人提供一个不错的起点,让他们自己来做。
5. 你们详细规划的时间跨度有多长?这些年来有何变化? Perplexity成立不到两年,而AI领域瞬息万变,很难给出两年之外的承诺。
我们一般会制定季度计划,在季度内,我们尽量保持计划的稳定,并设定产品路线图。路线图上有大家熟知的几个大项目,以及随优先级变化而调整的小任务。
灵活应变至关重要,因为AI的发展常常会带来不可预见的影响。例如,开源模型和上下文长度的快速发展对产品、路线图和整个业务都产生了下游影响。就在最近,Meta发布了Llama 3,Mistral发布了8x22B,我们正在探索如何将这些模型创造性地应用到我们的产品中。
产品路线图中的项目也需要灵活一些,因为新产品开发与技术/模型开发路线图是一起进行的。工程师会根据每周的情况决定是维护现有产品还是构建新产品。技术路线图通常发展很迅速,因为我们会遇到现有系统的限制并且会累积技术债务,但一般优先处理能够带来产品改进的技术债务。
尽管如此,一周之内的计划还是相对稳定的。我们每周都有一个启动会议,每个人都会设定本周的宏观期望。我们有一个“75%”的企业文化:大家都挑出本周的首要任务,并尽力达到75%的完成率。只需几个要点,就能确保本周的优先事项清晰明确。
在每周开始时花点时间思考核心任务可以让逻辑清晰,并避免出现决策仓促、决策混乱。随着时间的推移,我们根据投资回报评估项目规模和优先级的能力也有所提高。
6. 你们会以某种形式使用OKR吗? 我们尽量在季度计划中以数据驱动,并且对此很严格。所有目标都是可以衡量的,无论是定量的阈值,还是布尔值“X是否完成”。
目录 查看当前数据库含有表查看表结构创建表插入(新增create)全列插入:指定列插入插入查询结果 查询(retrieve)全列查询指定列查询查询列是表达式别名查询(as)去重查询(distinct)排序查询(order by)条件查询(where)比较/逻辑运算符使用 分页查询(limit) 一条语句各查询间的使用顺序修改(update)删除(delect) 在对数据库中的表进行操作前都需要先使用该数据库: use 数据库名; 查看当前数据库含有表 show tables; 该语句可以将当前数据库含有的所有表的表名显示出来。
查看表结构 desc 表名; 可以查看该表中的字段以及其类型。
创建表 语法:
create table 表名( 字段1名 数据类型1, 字段2名 数据类型2, 字段3名 数据类型3, ); 创建商品goods(商品编号goods_id,商品名goods_name, 单价unitprice, 商品类别category, 供应商provider):
插入(新增create) insert into 表名 (列名) values (对应数据); 全列插入: 数量必须和定义表的列的数量及顺序一致,
前面可以省略列名,
插入多行数据时每行数据都要用括号括起来,括号之间使用逗号隔开。
insert into goods values (1,'面包',15.5,'食物','大润发');#插入单行数据 insert into goods values (2,'黄瓜',5.5,'蔬菜','大润发'), (3,'白菜',1.5,'蔬菜','大润发');#插入多行数据 指定列插入 数量必须和指定列数量及顺序一致。
未指定的列默认插入null。
insert into goods (goods_id, goods_name,unitprice) values (3,'衣服',155); insert into goods (goods_id, goods_name,unitprice) values (4,'裤子',105),(5,'鞋子',200); 插入查询结果 insert into 待插入表名 列名1,列名2 查询语句; 查询结果与列要对应(数量,类型一一对应)。
在面向对象编程中,随着系统的复杂度增加,对象之间的交互也会变得更加复杂。这不仅增加了系统的维护难度,也降低了系统的可扩展性。设计模式中的中介者模式就是一种用来简化对象间交互的有效方法。本文将详细介绍中介者模式的原理、结构以及应用场景,并通过一个简单的示例来加深理解。
中介者模式概述 定义:中介者模式是一种行为型设计模式,它定义了一个对象来封装一系列对象之间的交互,从而降低对象间的直接依赖,使它们不需要显式地相互引用,可以独立地改变它们之间的交互。
目的:通过引入一个中介者对象来集中处理原本分散在多个对象间的交互逻辑,从而降低系统各组件间的耦合度。
适用场景:
当一个系统中存在大量对象之间相互依赖的情况时。需要动态地改变对象之间的交互方式。 模式结构 参与者:
Mediator(中介者接口):定义统一的方法与同事对象通信。Concrete Mediator(具体中介者):实现中介者接口,协调同事对象的行为。Colleague(同事类):每一个同事都实现了发送消息给中介者对象的接口;每个同事对象都不与其他同事对象显式通信,而是与中介者对象通信。 交互流程:
同事对象向中介者发送请求。中介者根据请求调用相应的同事对象方法,实现对象间的交互。 示例代码 假设创建一个聊天室应用程序,其中包含多个用户。为了方便管理用户的聊天行为,使用中介者模式来实现。
代码实现
// 定义中介者接口 public interface ChatMediator { void send(String msg, User user); } // 具体中介者实现 public class ChatRoom implements ChatMediator { @Override public void send(String msg, User user) { System.out.println(user.getName() + ": " + msg); } } // 定义同事类接口 public interface User { String getName(); void sendMessage(String message); } // 具体同事类实现 public class Person implements User { private String name; private ChatMediator mediator; public Person(String name, ChatMediator mediator) { this.
How to adjust a PID controller in Arduino We continue with this mini-series of posts dedicated to control systems in Arduino. The most feared moment for many arrives, making the adjustment or tuning of the PID.
In previous posts, we have seen what a controller is, hysteresis control, and we have introduced the powerful PID controller. We emphasize that, without being the perfect controller, the PID is popular for being relatively simple and achieving good behavior in a large number of plants, without knowing their nature.
最近AutoGPT不是更新了嘛
安装 我按照官方的教程
在本地搭建好了
改动 可见的改动,主要是把原来的纯命令行改成前后端的形式
看下前端界面
界面比较简单,主要分3个大块
监控 第一个是监控
主要是看你在 build 里构建的Agents的运行情况
build 第一个是Agents构建界面
里面有很多可选的block
其实就是工作流,不过这玩意,没啥问题,也没提示
我也没摸索明白
有大佬知道,可以分享下
市场 第三个是市场,说白就是你可以用别人构建好的agent
但是目前现在啥也没有
最后 个人感觉和coze、fastgpt之类很像,都是工作流的形式
不同的是AutoGPT可以支持代码
功能上比上面要少很多,也可能是我不大了解
AutoGPT是可以自主创建任务的,这种工作流的模式不是很理解干啥有,有大佬分享下经验嘛
各位有啥不同的想法的也可以留言交流!
本文由 mdnice 多平台发布
backbone CCFF 还不知道网络连接方式,只是知道了每一层
backbone
backbone.backbone.conv1.weight torch.Size([64, 3, 7, 7])backbone.backbone.layer1.0.conv1.weight torch.Size([64, 64, 1, 1])backbone.backbone.layer1.0.conv2.weight torch.Size([64, 64, 3, 3])backbone.backbone.layer1.0.conv3.weight torch.Size([256, 64, 1, 1])backbone.backbone.layer1.0.downsample.0.weight torch.Size([256, 64, 1, 1])backbone.backbone.layer1.1.conv1.weight torch.Size([64, 256, 1, 1])backbone.backbone.layer1.1.conv2.weight torch.Size([64, 64, 3, 3])backbone.backbone.layer1.1.conv3.weight torch.Size([256, 64, 1, 1])backbone.backbone.layer1.2.conv1.weight torch.Size([64, 256, 1, 1])backbone.backbone.layer1.2.conv2.weight torch.Size([64, 64, 3, 3])backbone.backbone.layer1.2.conv3.weight torch.Size([256, 64, 1, 1])backbone.backbone.layer2.0.conv1.weight torch.Size([128, 256, 1, 1])backbone.backbone.layer2.0.conv2.weight torch.Size([128, 128, 3, 3])backbone.backbone.layer2.0.conv3.weight torch.Size([512, 128, 1, 1])backbone.backbone.layer2.0.downsample.0.weight torch.Size([512, 256, 1, 1])backbone.backbone.layer2.1.conv1.weight torch.Size([128, 512, 1, 1])backbone.backbone.layer2.1.conv2.weight torch.
随着数据量的迅猛增长,企业和组织在数据库管理方面遭遇的挑战愈发凸显。数据库性能逐渐下滑、存储成本节节攀升,以及数据运维复杂性的增加,这些挑战使得DBA和开发者在数据管理上面临更大的压力。
为了应对这些挑战,对数据生命周期实施更为细致的管理变得至关重要。这包括从在线处理到近线存储,再到归档整理,直至数据销毁的整个生命周期管理。在这一系列阶段中,近线阶段和归档阶段的历史库管理显得尤为重要。本文将深入探讨如何对历史库进行现代化架构升级,并重点聚焦于OceanBase如何帮助企业优化数据库历史库管理。
一、构建满足现代需求的数据库 历史数据存储在近线和归档阶段都发挥着重要作用。在归档阶段,可采用数据库或离线文件的形式。而对于仍需进行少量查询的归档数据,则通常选择历史库方案。历史库方案实际上是实现冷热数据分离的策略,通过减轻在线库负担来提升其性能。历史库的冷数据通常具有低频访问的特点,所以可以选择磁盘空间较大、CPU 配置较低的机型,以实现成本节约的目的。
历史库的引入给数据库管理系统带来了新的挑战,我们对此的理解主要来自于用户对数据管理解决方案的迫切期待。在与用户的交流中,我们发现许多用户迫切需要一种能够有效处理大规模历史数据的解决方案,同时希望在降低成本的同时不影响性能和数据可用性。这些反馈深刻地影响了我们对历史库的理解。因此,我们期望历史库能够具备以下特点:
○ 大容量的存储空间,支持大量数据的存储和在线库数据高效持续导入。
○ 具备良好的可扩展性,能够处理不断增加的数据量而无需调整存储架构。
○ 提供更低的存储成本,以更少的磁盘空间和更经济的存储介质存储更多数据。
○ 提供一定的查询能力,支持高效的少量事务型查询,同时也能够支持高效的分析型查询。
○ 对应用和在线库保持相同的访问接口,降低应用复杂度。
当面对这些需求时,OceanBase 成为一种天然的选择。其具备良好的单机分布式扩展能力和 HTAP 混合负载处理能力,使其能够高效地支持业务系统的在线库和历史库场景。更为重要的是,OceanBase 在满足业务需求的同时,能够至少降低一半的存储成本。据部分客户反馈,将业务历史库从其他数据库迁移至 OceanBase 后,存储成本可降低 80%左右,这也是许多用户在历史库场景选择 OceanBase 的主要原因之一。
图 1:OceanBase 历史库产品架构
随着历史库产品架构的设计,我们进一步思考历史库的存储架构问题。
首先,关于历史库的数据库架构是否需要与在线库保持一致的问题,我们认为不需要。在线库可能出于数据规模和性能的需要,采取分库分表等架构,但历史库的性能要求通常较低。分库分表架构对数据库的部署运维、备份恢复都带来额外的成本。特别是采用 OceanBase 作为历史库时,单表轻松承载几十 TB 的数据规模,即使数据规模很大也可以采用分区表。
其次,关于历史库是否应该支持数据更新的问题,技术上是可行的,历史库可以支持更新,也可以设定为只读。然而,从历史库整体成本的角度考虑,我们建议尽量采用只读历史库的方案。只读历史库随机读写更少,可以使用更廉价的存储硬件,如 SATA 盘而不是 SSD。此外,只读历史库也降低了历史库自身的备份成本,只需要维护一份备份副本。
最后,对于数据归档应尽可能减少对在线库的影响的问题,这是非常重要的。在线库是企业业务持续稳定运行的关键,在数据规模较大的场景下,大批量数据的读取、计算、删除会给在线库造成压力,因此数据归档过程必须能够保障在线库的稳定性。
二、OceanBase 数据归档的核心能力 (一)冷热数据分离,提升在线库性能 通常情况下,一部分业务数据在一段时间后就很少被访问或者不再被访问(我们称之为“冷”数据)。解决思路是将访问频率较低的“冷”数据归档到历史库中,而在线库则只保留最近某一段时间的数据。
传统的数据归档方式常常需要耗费大量的时间和人力,并且存在操作错误、数据丢失等风险。此外,手动归档操作的繁琐性也限制了数据管理的效率和工作的灵活性。面对这些问题,ODC 从 4.2.0 版本引入了数据归档功能,旨在解决数据管理中的难题,提高工作效率和数据安全性。下面,我们将使用 ODC 的数据归档功能来实现这一冷热数据分离的过程:
(二)新建「数据归档」工单 在 ODC 中,点击「工单」-> 「新建工单」-> 「数据归档」,进入数据归档工单的创建页,填写工单详情。这里我们配置了 tb_order 表从在线库到历史库的归档任务,勾选了归档完成后清理源端已归档数据。注意这里使用了变量 archive_date,其值设置为当前时间往前偏移 1 年,通过在过滤条件中引用变量的方式,可以实现每次执行归档任务都归档 1 年前的数据。
图 2:新建数据归档任务
ODC 数据归档支持多种执行调度策略,可以立即执行、指定时间执行,也可以周期执行。还支持配置结构同步、数据插入策略和限流策略。结构同步时可根据需要选择是否同步分区和索引,因为历史库可能会和在线库有不同的分区设计,历史库和在线库的查询需求也不一样也可以通过更少的索引进一步降低存储成本。
图 3:数据归档任务设置
关于线性回归建模,线性回归分析中,回归方程的检验是?
A. t检验
B. 卡方检验
C. F检验
D. 正态检验
数据分析认证考试介绍:点击进入
题目来源于CDA模拟题库
点击此处获取答案
数据分析专项练习题库
内容涵盖Python,SQL,统计学,数据分析理论,深度学习,可视化,机器学习,Spark八个方向的专项练习题库,数据分析从业者刷题必备神器!
在软件开发中,我们经常会遇到一些算法步骤固定但某些步骤需要由子类具体实现的场景。为了避免重复代码并确保逻辑一致性,模板方法模式(Template Method Pattern) 提供了一种优雅的解决方案。本文将详细探讨模板方法模式的定义、应用场景、优点以及如何在实际项目中使用这一模式来编写更加灵活和可维护的代码。
一、模板方法模式概述 模板方法模式是一种行为型设计模式,它允许你在父类中定义一个算法的骨架,并将某些步骤的实现延迟到子类中。这样一来,子类可以重新定义算法的某些步骤,而不会改变算法的整体结构。
1.1 模板方法模式的结构 模板方法模式主要包括以下几个部分:
抽象类(Abstract Class):定义算法的骨架,并包含一个模板方法(template method)。模板方法定义了算法的步骤,并调用抽象方法来完成这些步骤。具体子类(Concrete Classes):继承抽象类,实现其未实现的抽象方法,从而完成算法的具体步骤。 下图展示了模板方法模式的典型结构:
┌────────────────────┐ │ AbstractClass │ │────────────────────│ │+ templateMethod() │ │────────────────────│ │+ primitiveOperation1() │ │+ primitiveOperation2() │ └────────────────────┘ ▲ │ ┌────────────────────┐ │ ConcreteClass │ │────────────────────│ │+ primitiveOperation1() │ │+ primitiveOperation2() │ └────────────────────┘ 1.2 模板方法模式的优点 代码复用:将通用的算法逻辑放在抽象类中,避免子类之间重复相同的代码。控制流程:抽象类中的模板方法控制着整个算法的流程,确保逻辑的一致性,而具体的实现细节则由子类来提供。灵活性:子类可以根据需要覆盖父类中的方法,从而改变或扩展算法的某些步骤。 二、模板方法模式的应用场景 模板方法模式适用于以下场景:
算法步骤固定:当一个算法的步骤在高层次上是固定的,但某些步骤需要在子类中实现时,可以使用模板方法模式。避免重复代码:在多个子类中存在相似的代码或逻辑时,可以将相同的部分提取到父类中,而将不同的部分留给子类实现。标准化流程:当需要确保某个操作流程在各个子类中保持一致性时,可以使用模板方法模式来统一流程。 三、模板方法模式的实现 接下来,我们通过一个简单的例子来展示如何在实际开发中使用模板方法模式。
假设我们正在开发一个文档处理系统,不同类型的文档(如Word文档、PDF文档)有相似的处理流程,但每种文档格式的读取和保存方式不同。我们可以使用模板方法模式来实现这一需求。
3.1 定义抽象类 首先,我们定义一个抽象类DocumentProcessor,它包含了处理文档的通用步骤(读取、处理、保存),并定义了一个模板方法processDocument()。
public abstract class DocumentProcessor { // 模板方法,定义了处理文档的步骤 public final void processDocument() { openDocument(); parseDocument(); saveDocument(); } // 抽象方法,由子类实现 protected abstract void openDocument(); protected abstract void parseDocument(); protected abstract void saveDocument(); } 3.
随着宠物健康科技领域的快速发展,智能听诊器以其便捷和智能的特性,彻底革新了居家宠物健康监测的方式。 蓝牙连接:宠物主人只需通过手机蓝牙连接,即可轻松获取宠物的心率、呼吸频率等关键生命体征数据。高精度传感器:设备内置的高精度传感器能够精准捕捉宠物的心跳,配合先进的算法,实时转化为易于理解的健康报告,并直接发送到主人的智能手机上。 实时监测与预警 智能听诊器最引人注目的功能是其实时监测能力。无论是宠物的日常活动还是休息时刻,主人都可以通过蓝牙连接实时监测宠物的健康状况,并在宠物出现健康问题的初期阶段发出预警,为及时采取措施提供可能。
云端同步与数据管理 云端同步:智能听诊器的云端同步功能让宠物的健康数据得以长期保存和深入分析,为宠物的健康管理提供了宝贵的历史数据支持。历史数据支持:这些数据无论是在家中自我监测,还是到兽医诊所进行专业检查,都能提供详实的参考依据。 我们期待着,随着科技的不断进步,智能听诊器将为我们带来更多惊喜,让宠物的健康监测变得更加智能化、便捷化。
数据结构初阶最终讲:排序 1.排序的概念及其运用1.1什么是排序1.2排序的运用1.3常见排序算法 2.冒泡排序3.直接插入排序4.堆排序5.测试代码:排序性能对比5.1直接插入排序时间复杂度分析 6.希尔排序6.1希尔排序时间复杂度分析 7.选择排序7.1初步思路7.2选择排序优化7.2.1初步实现7.2.2出错点17.2.3出错点27.2.4出错点37.2.5选择排序优化最终代码 7.3选择排序时间复杂度分析 8.快速排序--Hoare版本8.1.1代码的初步实现8.1.2错误点18.1.3错误点28.1.4错误点38.1.5错误点48.1.6错误点58.1.7错误点68.1.8错误点7 8.2Hoare版本快排最终代码8.3快速排序空间复杂度分析8.4快速排序时间复杂度分析8.4.1最优情况(平均情况)8.4.2最坏情况 8.5观察快速排序的排序时间 9.快速排序--挖坑法10.快速排序--lomuto前后指针11.快速排序--非递归版本12.归并排序12.1归并排序时间复杂度分析12.2归并排序空间复杂度分析 13.非比较排序--计数排序13.1非比较函数时间复杂度分析 14.排序算法复杂度以及稳定性分析 这一讲是数据结构初阶的最后一讲了,当然也是很有难度的一讲,是对于排序算法的总篇章,当然,会有其它更好的排序算法,但是对于初阶的数据结构来说,先学习这些就足够了
1.排序的概念及其运用 1.1什么是排序 排序,顾名思义,就是对一串数据,按照某个特定的顺序,将这一串数据进行有序排列的方法
1.2排序的运用 排序在我们日常生活中的使用十分广泛
当我们在网上购物,筛选自己心仪的产品时,就使用到了排序:
当我们在考试完后看自己的成绩排名时,也会用到排序:
1.3常见排序算法 下面是一些常见的排序算法,这一讲会将这些排序算法逐一实现
2.冒泡排序 冒泡排序对于教学来说很有意义,至少是我所学过的第一个排序算法,但是使用起来非常麻烦,它的时间复杂度为O(n^2),是一个非常大的复杂度值了
//冒泡排序 void BubbleSort(int* arr, int n) { //冒泡排序十分经典,而且使用很少,所以不再讲解,这里只会作为一个对比 for (int i = 0; i < n-1; i++) { int def = 0; for (int j = 0; j < n - i - 1; j++) { if (arr[j] > arr[j + 1]) { Swap(&arr[j], &arr[j + 1]); def = 1; } } //当没有一个数据交换时,表示已经排序完了,直接退出即可 if (def == 0) { break; } } } 3.
在Ubuntu Linux(例如 Ubuntu 24.04、22.04 或 20.04)上安装Go(Golang)是一个简单的过程。我们可以使用默认系统存储库使用本教程中给出的命令下载开源 Go 编程语言,轻松构建简单、可靠和高效的软件。
Go语言由Google设计,它结合了编译语言的速度和动态语言的易用性,使其成为从 Web 服务器到数据分析等各种应用的理想选择。Ubuntu Linux 因其开源特性和强大的社区支持而在开发者社区中越来越受欢迎。因此,为什么不用它来开发 Go 应用程序呢……
安装 Golang有三种简单方法- 一种是使用默认系统存储库,另一种是使用PPA 存储库及其Tarball 文件。让我们看看如何使用它们。
注意:如果没有Ubuntu服务器,可以考虑雨云,1元即可试用,需要绑定微信,支持多种Linux发行版。
优惠注册地址:www.ecscoupon.com/rainyun
#第一种方法,使用系统默认存储库
使用 Apt 更新 Ubuntu Linux 由于我们即将使用系统存储库来安装 Go Lang,因此建议首先运行系统更新命令。它将重建 APT 的包索引缓存,并安装最新更新(如果有)。
sudo apt update 使用 APT repo 安装 Go Lang 是的,虽然 GO Lang 可通过 Ubuntu 的默认存储库获得,但通过它获得的版本不是最新版本。因此,如果您正在寻找最新的 Go 版本,请使用第二种或第三种方法来安装它,而不是这种方法。
sudo apt install golang #第二种方法,使用 PPA 存储库:
添加 Go PPA 存储库 为了使用默认的 Ubuntu 包管理器(即 APT)快速获取 Ubuntu 上最新的 Go 编程版本以及未来的更新,我们可以添加一个 PPA 存储库,以下命令:
原创 | 刘教链
隔夜BTC继续拉涨,急破6万刀,“过了黄洋界,险处不须看”,一度逼近63k,目前暂于61-62k区间休整。从8月5日极限插针下探49k,仅仅3天多时间,就连续拉涨到了61k,总涨幅接近25%。
不知道这种3天拉涨25%的机会,一年里能有几次,一个人的整个投资生涯中又能满仓把握住几次?所以,教链在8月5号暴跌恐慌之际,于当日文章《暴跌,洗牌!》中直言不讳地写道:
劝人割肉,非蠢即坏。
如果一个小白,害怕之时听了割肉的鼓动,在49k清仓,那么仅仅3天后,在61k买回,就立即损失接近1/5的BTC,也就是损失了20%的仓位。5个BTC割肉,3天之后还剩4个BTC。
3天损失1个BTC。
而如果他不买回,那么随着BTC的继续拉涨,他的损失将越来越大。等BTC升至98k,他将损失一半的BTC。但就算BTC再次探低到49k,他可能依旧不敢买回,因为那个时候,一定会有更多的声音告诉他,BTC还将继续下跌,30k、20k、……
最后的结局,很可能是他永远失去仓位,失去BTC。
待到8月7号,教链又在《大跌见真金,BTC还能再创新高吗?》一文中,复盘2020年“312”和2021年“519”的暴跌模式,对照分析本次洗盘。文中指出:「如果说,今年2024年在BTC周期上的时空位置,更接近2020年的话,那么从概率上讲,押韵“312”的可能性或许会更大一些。」
再到昨晚[8月8号教链内参“空头是否已三振出局?”],教链进一步对2021年“519”暴跌模式进行了细细的品味,重温了2021年7月22日所写的《空头三振出局》一文。
请注意《空头三振出局》的发表时间点。标记到K线图上来看一下:
在2021年7月22号的时候看这个图,可不是上图这样子的,而是下图这样子的:
因此,昨晚[“8.8教链内参:空头是否已三振出局?”]翻译一下就是:
8.5暴跌也许并非“519”,而是“722”?
这无疑是一个极为大胆的假设。
在“信仰-怀疑”阶段,多空观点的交锋必然是激烈的。
自从2024年3月13-14日BTC局部触顶73.8k之后,至今已经洗盘5个月。
如果参考当年黄金ETF上市后,局部触顶后长达10个月的洗盘期,那么目前BTC依然是“半渡”。
黄金ETF洗盘通道,在7个月前教链2024.1.9文章《比特币大伏大起》中给出了图示:
不管是三振也好,五振也罢,通过[“8.5教链内参:全球暴跌之下,教链评估BTC的几个关键点位”]中的评估测试,可以几乎肯定的是,空头对3万刀甚至2.5万刀乃至于本轮牛市已结束的幻想,是终将要随着BTC的不断续创新高而被击得粉碎的了。
7月内参合订本 & 8.8内参:空头是否已三振出局?
阅读更多内参,请加入刘教链的知识星球:
* * *
延伸阅读更多刘教链精彩文章:
【攻略】币圈破产指南 2019.6.15
小杂感 2021.6.30
牛市熊了么? 2021.7.6
下雨和交易 2021.6.25
不动如山,方得始终 2021.1.13
比特币趋势大反转 2024.5.16
春江水暖鸭先知 2021.6.4
草根的力量,庶民的胜利 2023.11.9
比特币天天向上 2023.1.30
(公众号:刘教链。知识星球:公众号回复“星球”)
(免责声明:本文内容均不构成任何投资建议。加密货币为极高风险品种,有随时归零的风险,请谨慎参与,自我负责。)
喜欢本文就请点亮在看、点赞、转发支持哦
👇👇👇
欢迎来到我的Blog,点击关注哦💕
前言 string vector list 这种线性结构是最基础的存储结构,C++(STL)container很好的帮助我们数据存储的问题。
容器适配器 介绍 容器适配器是C++标准模板库(STL)中的一种设计模式,它允许将一个容器的接口转换为另一个接口,从而提供不同的操作和行为。容器适配器通常用于封装现有容器,以实现特定的数据结构特性,如栈(后进先出)、队列(先进先出)和优先队列(根据优先级排序)。 应用 栈(stack):栈是一种后进先出的数据结构,其操作包括入栈(push)、出栈(pop)、查看栈顶元素(top)等。栈适配器可以基于多种底层容器实现,如vector、deque或list.
队列(queue):队列是一种先进先出的数据结构,其操作包括入队(push)、出队(pop)、查看队首元素(front)和查看队尾元素(back)。队列适配器同样可以基于deque或list实现,以适应不同的性能需求.
优先队列(priority_queue):优先队列是一种特殊的队列,它根据元素的优先级进行排序。其底层容器通常是vector或deque,并通过堆算法维护元素的优先级顺序。优先队列适配器提供了插入和删除具有最高优先级元素的操作.
双重结束队列(双端队列(deque)) 特点 双端操作效率:支持在两端进行快速的插入和删除操作。随机访问:可以通过索引直接访问容器中的元素。无需预先分配固定大小:与vector不同,deque不需要在创建时指定大小,它可以根据需要动态增长。内存分配策略:deque不需要像vector那样一次性分配大量内存,而是分散在内存中,这有助于减少内存碎片。 存储结构 双端队列底层是一段假象的连续空间,实际是分段连续的,为了维护其“整体连续”以及随机访问的假象,落 在了deque的迭代器身上,因此deque的迭代器设计就比较复杂,如下图所示:
List 、vector deque对比 对比维度VectorDequeList内存连续性是否否随机访问性能O(1)O(1) 但可能不如VectorO(n)插入/删除性能非末尾O(n)两端O(1), 中间O(n)两端及中间O(1)内存重用效率扩容时需移动元素两端添加删除不需移动不适用内存分配模式动态数组,连续内存分段连续内存非连续内存迭代器失效可能不会不会支持的操作[] 访问、.at() 等[] 访问、.at() 等[] 访问、.at() 等内存管理开销高(扩容时)中等(两端操作)低适用场景需要快速随机访问且元素数量稳定需要两端快速插入删除,随机访问需求适中频繁插入删除,不关心随机访问 栈(stack) 栈的介绍 函数说明接口说明stack()构造空的栈empty()检测stack是否为空size()返回stack中元素的个数top()返回栈顶元素的引用push()将元素val压入stack中pop()将stack中尾部的元素弹出 栈的模拟实现 利用容器适配器的设计原理,很容易实现栈
将栈放mystack的命名空间,以防止和库中冲突类模板设计container可以给缺省参数,默认deque(容器适配器)在里面利用deque的接口实现 namespace mystack { template<class T, class Container = std::deque<T>> class stack { public: void push_back(const T& x) { _con.push_back(x); } void pop() { _con.pop_back(); } size_t size() { return _con.size(); } T& top() { return _con.
解决办法:
1、打开Android Studio 右上角点击 SDK Manager。
2、SDK Manager 界面如下,选择Android SDK
3、找到 SDK 的安装位置,
4、到目录下找到build tools 目录,讲d8.bat 改成dx.bat
5、lib 目录更改d8.jar 为 dx.jar
关键字 continue continue 关键字用于控制循环语句的执行流程。当continue 语句被执行时,它会跳过当前循环迭代中剩余的代码,并立即开始下一次迭代。continue 通常用于 for、while 和 do-while 循环中。
#include <iostream> using namespace std; int main() { for (int i = 0; i < 10; i++) { if (i % 2 == 0) { continue; // 跳过本次循环剩余的代码,继续下一次循环 } cout << i << " "; } return 0; } 在这个例子中,continue 语句会使程序跳过 i 为偶数的情况,因此只会打印奇数:1 3 5 7 9。 static static 关键字在C++中有多种用途,分别可以应用于变量、函数和成员变量或成员函数。 1.静态局部变量 :静态局部变量是在函数内部定义的,但它们的生命周期跨越整个程序的运行时间。它们在第一次执行时初始化,并且其值在函数调用之间保持不变。
#include <iostream> void demo() { static int count = 0; // 静态局部变量 count++; std::cout << "
子窗体构造函数中加上下面这句话:
setWindowFlags(Qt::Window);
就好使了。
以下是解释:
`setWindowFlags(Qt::Window);` 这句话用于设置窗口的属性。`Qt::Window` 是一个窗口标志(`Qt::WindowFlags`),它指定了窗口的类型和行为。
具体来说,`setWindowFlags(Qt::Window);` 主要有以下几个作用:
1. **使窗口独立**:`Qt::Window` 标志使得窗口成为一个顶层窗口,而不是一个嵌入在其他窗口中的小部件(widget)。这意味着该窗口将有自己的标题栏、边框,并且可以独立于其他窗口移动和调整大小。
2. **避免嵌入式显示**:如果没有设置 `Qt::Window`,窗口可能会作为父窗口的一部分显示,而不是一个独立的窗口。通过设置这个标志,可以确保窗口不会嵌入在父窗口中,而是作为一个独立的窗口显示出来。
3. **提供默认的窗口管理行为**:设置 `Qt::Window` 后,窗口将遵循系统的默认窗口管理行为,如可以被最小化、最大化、关闭等。
在你的场景中,通过 `setWindowFlags(Qt::Window);`,你确保了子窗体 (`CMy`) 作为一个独立的窗口显示,而不会嵌入在父窗口中。这就是为什么子窗体在设置这个标志后能够正常显示的原因。
在能源转型与绿色低碳发展的全球浪潮中,国内领先的储能解决方案供应商海博思创以卓越的技术实力和前瞻性的战略眼光,站在了行业变革的前沿。公司不仅在国内外多个重要展会上大放异彩,更通过一系列技术创新与深度合作,为全球能源行业的可持续发展注入了新的动力。
在近期的欧洲智慧能源展(The Smarter E Europe)上,海博思创以“AI赋能储能价值新生”为主题,向全球展示了其最新的储能技术和全场景处理方案。展出的HyperBlock Ⅲ、HyperCube Ⅱ及HyperCube Pro等系列产品,凭借其独特的设计和出色的性能,吸引了众多国际同行的关注。其中,HyperBlock Ⅲ作为新一代5MWh交直流一体全液冷储能系统,通过将电池模块与模块化PCS融于一柜内设计,极大地提升了系统的安全性、效率与成本效益,成为展会上的明星产品。
海博思创不仅在硬件产品上持续创新,更在智能化管理领域取得了显著成果。公司自主研发的海博AI云,通过全息数据采集和全景运行感知,实现了对储能系统的全面监控和智能化管理。该技术体系还构建了数字孪生体系,有效提高了储能产品的运营效率和经济性,为全球能源行业的数字化转型提供了有力支持。
此外,海博思创还积极参与国际交流与合作,与全球能源行业的同仁共同推动能源科技的进步与发展。在6月6日举办的2024年施耐德电气创新峰会上,海博思创联合创始人、副总经理舒鹏参与了以“聚合生态力量,共塑发展新动能”为主题的圆桌论坛,深入剖析了能源产业的未来发展趋势,并分享了海博思创在储能技术与智能电网领域的创新成果。舒鹏指出,数字化与绿色低碳“双转型”已成为不可逆转的发展潮流,而促进生态圈上下游协同、合作伙伴强强联合,将是企业提升竞争力、推动业务发展的关键。
海博思创自成立以来,始终致力于为全球能源行业提供高质量的储能解决方案。公司凭借精准管理电池能效的技术,为传统发电、新能源发电、智能电网、终端电力用户及智能微网等“源—网—荷”全链条行业客户提供了全系列储能系统产品,以及储能系统一站式整体解决方案。这些解决方案不仅具备高度的灵活性和可扩展性,还具备高效、安全、智能等特点,赢得了国内外市场的广泛赞誉。
展望未来,海博思创将继续秉承“创新、卓越、服务”的理念,持续推动储能技术的发展和应用。公司将不断加大在储能技术、智能电网等领域的研发投入,探索储能技术的更多可能性,并计划在未来几年内推出更多创新产品和解决方案。同时,海博思创还将积极参与国际交流与合作,与全球能源行业的同仁共同推动能源科技的进步与发展,为构建绿色低碳、可持续发展的全球能源体系贡献力量。
1- 思路 使用递归 dfs 实现① 递归思路:每次递归返回值为 , root.val+Math.max(left,right) 从 左右孩子中挑选一个大的。② 递归公式:定义 sum,sum = root.val + left + right 2- 实现 ⭐124. 二叉树中的最大路径和——题解思路 class Solution { int maxSum = Integer.MIN_VALUE; public int maxPathSum(TreeNode root) { // 递归 dfs(root); return maxSum; } public int dfs(TreeNode root){ // 1. 终止条件 if(root==null){ return 0; } // 2. 递归公式,递归逻辑 int left = dfs(root.left); int right = dfs(root.right); int sum = root.val + left + right; maxSum = Math.
uniapp本地打包app安装说明 目录 uniapp本地打包app安装说明一、打包说明1.HBuilder X 生成本地打包资源2.Android Studio和App离线SDK环境准备2.1 下载Android Studio和 App离线SDK2.2 资源替换2.3 id属性值修改。2.4 添加provider信息到`AndroidManifest.xml`中的`<application>`节点2.5 包名设置。2.6 版本信息设置。2.7 证书签名信息设置。 3.Appkey申请4.Apk打包5.其他问题1、uniapp离线打包Android 10上无法启动相机 一、打包说明 本文档主要说明uniapp打包成apk的步骤,仅供参考。
项目打包需要使用到HBuilder X、Android Studio和Android SDK。
1.HBuilder X 生成本地打包资源 发行 – 原生App本地打包 – 生成本地打包App资源
(注:本地打包的项目代码文件名不能含有中文,如图片资源名字等,问就是本人亲身试过,另外iconfont打包的资源有直接引用的也需要注意icon的名称)
2.Android Studio和App离线SDK环境准备 2.1 下载Android Studio和 App离线SDK 官网路径:https://nativesupport.dcloud.net.cn/AppDocs/usesdk/android.html
(注意:下载的Android 离线SDK与本地开发工具版本对应)
下载后解压得到以下内容:
2.2 资源替换 使用Android Studio打开目录”HBuilder-Integrate-AS”(使用“HBuilder-HelloUniApp”也可以),并将HBuilder X生成的本地打包资源替换到“src/main/assets/apps”目录下
2.3 id属性值修改。 将dcloud_control.xml的appid值改为与manifest.json里面的id值相同,如图所示。
!!!!一共三个地方
2.4 添加provider信息到AndroidManifest.xml中的<application>节点 2.5 包名设置。 修改AndroidManifest.xml和build.gradle的值,如图3处位置的值要相同,这个包名要与后续在“开发者中心”设置“应用信息”时的“包名/appid/域名”一致。
2.6 版本信息设置。 build.gradle中的versionName和versionCode的值需要与manifest.json中的version信息对应上。
2.7 证书签名信息设置。 自3.1.10版本起需要申请Appkey配置项目,申请Appkey需要使用SHA1和SHA256。
可以使用Android Studio生成。
(注意:因为示例中有自己的默认配置“src/test.jks”,可以直接使用,或者自己新生成。)
填好信息,点击“ok”回到上一页,关闭,可以看到“src”目录下已经有新生成的“key.jks”文件。
然后到key.jks所在目录下打开cmd,执行命令keytool -list -v -keystore key.