打开网易新闻 查看更多图片

众所周知,给机器人编程相当困难,这通常需要具备专业技能的博士学位人才,成本也很高昂。

据此,我们来设想一下,如果每个人都能依照一个软件框架进行机器人编程,这会不会是一个理想化的方案?

从表面上看,这一想法并没有错,但我们不知道如何让这个方法更容易遵循——这就像你想发明一件隐形斗篷,并希望能够用你可以从超市购买其原材料。

目前的问题是:机器人编程有两大难点。

机器人很难,因为世界很复杂

打开网易新闻 查看更多图片

第一种困难,是机器人要处理大量现实世界的问题,但其感知和驱动都仍不完美。机器人的全局可变状态(Global mutable state)是一种糟糕的编程风格,它真的很难处理。

但其实,整个物理世界都是全局可变状态,你只能利用并不可靠的感知,期望其行为接近目标效果。

让机器人工作,经常会触及人类推理能力的极限。并且需要灵活地针对特殊问题采用启发式方法。这就是问题的内在复杂性:机器人生活在复杂的世界中,对于每一个可行的解决方案,背后都有数百万个不起作用的解决方案。

找到正确的解决方案很难,且往往非常依赖于任务、机器人、传感器和环境。

人们面对这一挑战,意识到其艰巨性,便认为或许只有某些顶尖的机器人专家能在某一特定情境下解决这些问题,但对于“普通人”呢?

不要为无定形群体设计

“非机器人专家”是一个模糊的、无定形的群体,我们不应为无定形群体设计一个定形的框架。

如果你不能说出对应的 API 是为具体哪几类人设计的,那么你就是在为一个无定形群体设计。

考虑到这个模糊的用户群体,或许有人会想,“我们可以通过设置简单的 API来解决。”

但是,你不能通过简单的API来掩盖内在复杂性,因为如果你的API很简单,它们就无法涵盖问题的复杂性。你最终会得到一个外观漂亮的API,包含如“grasp_object”和“approach_person”这样的调用,这些调用在黑客马拉松开幕式中演示得很好,但在某人真正尝试完成一些工作时,只能持续大约15分钟。

结果你会发现,对于一些特定应用来说,“grasp_object()”对“grasp”和“object”做出了3或4个错误的假设,对人们来说根本不起作用。

用户和你一样聪明

有一种普遍的刻板印象,即“用户不如创造这个神奇框架的人聪明”。这种优越感会让设计师坚持采用他们漂亮、简单的“grasp_object()”函数,并拒绝添加所需的旋钮和参数,来覆盖更多场景,并允许用户自定义功能。

具有讽刺意味的是,这反倒给可怜的 API 用户带来了许多复杂性,他们必须想出巧妙的解决方法才能让它正常工作。

打开网易新闻 查看更多图片

令人沮丧的是,这种框架即便能扩大使用人群,也需要牺牲一些性能,因为这些性能只有通过超级专业的解决方案才能获得。如果我们对机器人的需求非常大,但却只能由机器人专家编写程序,或许就只能接受牺牲性能。

但显而易见的事实是,在制造单元等真正受限的环境之外,即使是最优秀的机器人专家,在漫长的时间和大量的资金支持下,也难以接近使机器人具有商业可行性的性能水平,这意味着我们没有任何空间来牺牲能力和效率。

我们要解决什么问题?

那么,我们要不要放弃简化机器人编程呢?难道机器人开发只能是少数拥有高级学位精英的专属领地吗?对此,答案都是否定的!

我曾与许多本科实习生共事,他们完全有能力从事机器人研发工作,我自己在机器人编程方面也是基于自学。

尽管让机器人正常运行确实存在固有的复杂性,但我认为这并不比开发视频游戏更为艰难。

在机器人技术领域,和其他所有事物一样,经验是宝贵的,有些技能是可以传授的,当你掌握了众多领域的知识后,就能开始看到它们之间的联系。这些技能算不上神奇,也非机器人领域独有,我们并没有自己想象的那么特殊。

那么,如何让机器人编程变得更加简单呢?这要探讨的其中一方面是问题的内在复杂性,这部分无论怎样都会是困难的;而第二种是偶然的复杂性,我更愿意称之为“愚蠢的繁琐复杂性”

愚蠢又繁琐的复杂性

机器人是异步的、分布式的实时系统,带有奇特的硬件。

由于种种愚蠢的原因,配置这一切都会变得异常艰难。例如这些驱动程序需要在 Linux 的奇怪风格中工作,以便为控件提供硬实时性,而出于一些愚蠢的原因,完成所有设置将很困难。

又比如,你为了实现无缝漫游而不中断连接,对 Wi-Fi 进行了滥用,但 Linux 的 Wi-Fi 系统并不支持这样做。另外,日志文件很大,为了避免填满机器人的存储空间,你还得与某个云服务集成,处理它带来的种种愚蠢问题。

打开网易新闻 查看更多图片

在处理 3D 旋转、移动参考系、时间同步、消息传递协议等复杂问题之前,还有一大堆麻烦事要处理。

这些事情具有内在复杂性(例如考虑何时感知到某些事物,以及在其他事物移动时如何推理它)和愚蠢的繁琐复杂性(有一个奇怪的错误,因为有人以错误的顺序乘以了两个变换矩阵,现在你收到一条错误消息,指出在某些协议深处,四元数未标准化。这是什么意思?)。

机器人编程的最大挑战之一是涉足愚蠢的繁琐之海,你需要处理这些琐碎细节,才能开始处理有趣且具有挑战性的机器人问题。

因此,设计优秀 API 的一个简单准则就是:

为像你一样聪明、但对愚蠢的繁琐问题不那么容忍的人,设计 API。

当你使用自己制作的工具时,你会对它们非常了解,知道其中的缺陷,以及如何避免它们。

如果确定要构建一个机器人框架,就应努力使其功能尽可能强大,同时又尽可能减少无谓的繁琐,也就是尽力消除偶然复杂性,创建具有高灵活性但默认设置合理的API。

我喜欢Python的默认参数语法,因为这意味着你可以编写像下面这样使用的API:

打开网易新闻 查看更多图片

让简单的事情保持简洁,同时允许处理复杂的情况——请不要制作居高临下的 API。