←

最小的语言操作原子

📄 文章 🌐 公开 👁 83 次
📋 列表 ✏️ 编辑 🎨 画布版 📋 复制MD 🌐 复制HTML ☆ 收藏 🔊 TTS 🔗 复制链接

对,我觉得你的思路非常值得做实验。而且你说的“类似基函数”这个比喻很准确:不一定要直接把“句子理解”当成一个巨大任务,而是先寻找一组最小的语言操作原子,再观察复杂语言现象能不能由这些原子组合出来。

如果你的目标是测试一种新的 NLP 方法,我建议不要从“分词、词向量、Transformer”这些现成模块出发,而是从语言到底需要哪些基本操作来拆。

一、先把自然语言处理拆成几个最基本的动作

我会把它分成 7 类。

1. 指称:这个东西是谁?

最基本的问题:

“猫” → 一个对象/概念
“北京” → 一个地点
“他” → 某个已经出现的人

可以叫:

REFER(指称)

例如:

小明喜欢猫。

至少需要建立:

小明 → 人
猫 → 动物

2. 属性:它是什么样?

把一个对象和一个属性连接起来。

猫很大。

变成:

猫 → 大

或者:

小明很聪明。

小明 → 聪明

这是非常基础的操作:

ATTRIBUTE(x, a)


3. 关系:两个东西之间有什么关系?

例如:

小明喜欢小红。

实际上就是:

喜欢(小明, 小红)

再比如:

猫追老鼠。

追(猫, 老鼠)

我认为这是 NLP 中非常重要的一个“基函数”。

因为很多语言最终都可以还原成:

对象 + 对象 + 关系


4. 动作:某个东西发生了什么变化?

例如:

小明打开门。

不是简单的:

小明 → 打开
门 → 被打开

而是一个事件:

事件:
    动作 = 打开
    执行者 = 小明
    对象 = 门

也就是:

EVENT(action, agent, object)

复杂语言里的“事件”“过程”“因果”,可能都是从这个东西组合出来的。


5. 否定:不是

这是一个特别值得测试的基本操作。

小明喜欢猫。

喜欢(小明, 猫)

变成:

小明不喜欢猫。

NOT(喜欢(小明, 猫))

注意:

否定不是一个普通词,而是一种对已有结构进行操作的函数。

这就已经很接近你说的“基函数”了。


6. 组合:把两个东西组成一个更大的东西

例如:

红色的苹果

可以认为:

苹果
↓
ATTRIBUTE(苹果, 红色)

再比如:

小明喜欢红色的苹果。

就是:

喜欢(
    小明,
    ATTRIBUTE(苹果, 红色)
)

于是语言开始出现递归组合。

这可能才是你这个研究方向最核心的地方:

复杂语言未必需要新的基本运算,只需要已有运算不断组合。


7. 逻辑操作:如果、因为、所以、但是

再往上一层:

如果下雨,小明就不出去。

可以拆成:

IF(
    下雨,
    NOT(出去(小明))
)

再比如:

因为下雨,所以小明没有出去。

CAUSE(
    下雨,
    NOT(出去(小明))
)

再比如:

小明很聪明,但是他很懒。

AND(
    聪明(小明),
    懒(小明)
)

或者:

CONTRAST(
    聪明(小明),
    懒(小明)
)

于是:

否定、条件、因果、并列、转折,都可以成为更高层的组合操作。


二、这样一来,可以建立一个“语言基函数表”

我甚至建议你先不要追求很多。

可以从下面这套最小集合开始:

基本操作 功能 例子
REFER 指向对象/概念 猫
ATTRIBUTE 对象具有属性 猫→黑
RELATE 建立关系 喜欢(小明,猫)
EVENT 表示事件 打开(小明,门)
NOT 否定 不喜欢
AND 合并 A并且B
OR 选择 A或者B
IF 条件 如果A,则B
CAUSE 因果 A导致B
COMPARE 比较 A比B大
TIME 时间关系 A之后B
SPACE 空间关系 A在B里面

然后刻意限制模型只能使用这些操作。

这就变成一个非常有意思的实验。


三、例如把一句很复杂的话“编译”一下

比如:

因为昨天晚上下了很大的雨,所以小明没有去公园,但是小红去了。

可以逐层拆:

雨(昨天晚上)

大雨(昨天晚上)

去(小明, 公园)

NOT(去(小明, 公园))

去(小红, 公园)

CAUSE(
    下雨(昨天晚上),
    NOT(去(小明, 公园))
)

CONTRAST(
    NOT(去(小明, 公园)),
    去(小红, 公园)
)

注意这里发生了一件很重要的事情:

句子本身没有消失,只是被转换成了一个结构。

那么你的新 NLP 方法就可以测试:

给定这套基础操作,能不能重新生成原来的语言?

如果可以,就出现了:

自然语言
   ↓
基本操作
   ↓
组合结构
   ↓
复杂语义
   ↓
自然语言

这实际上已经非常接近一个“语言编译器”的思想。


四、我觉得你真正应该测试的不是“理解”,而是“组合能力”

这是我认为你这个想法最有意思的地方。

传统 NLP 很容易测试:

“这句话是什么意思?”

但你可以换一个问题:

一个语言系统能不能只用少量基本操作,组合出越来越复杂的语言结构?

例如规定只有:

A = 指称
B = 属性
C = 关系
D = 否定
E = 因果
F = 条件

然后测试:

一级

猫
红猫
猫吃鱼

二级

红猫吃鱼
小明喜欢红猫
小明不喜欢红猫

三级

因为小明喜欢红猫,所以他买了一只。

四级

如果小明喜欢红猫,那么当他看到红猫的时候,他就会买一只。

五级

如果小明喜欢红猫,那么即使价格上涨,只要他认为这只猫值得,他仍然会购买。

然后观察:

复杂程度增加以后,你的算法需要增加新的基本函数吗?

如果不需要,只需要不断组合已有函数——

那就非常有意思了。


五、甚至可以做一个“语言基函数实验”

我建议你第一版不要碰大型语料库。

自己做一个非常小的测试集。

比如只使用:

20个名词

人、猫、狗、鱼、苹果、汽车、学校……

20个关系

喜欢、吃、看、追、拥有、进入……

10个属性

大、小、红、蓝、聪明、漂亮……

10个逻辑操作

不、并且、或者、如果、因为、所以、但是……

然后随机组合。

例如:

猫 + 吃 + 鱼

小明 + 喜欢 + 猫

小明 + 不喜欢 + 猫

如果 + 小明喜欢猫 + 那么 + 小明买猫

因为 + 猫饿了 + 所以 + 猫吃鱼

然后逐渐增加组合深度:

深度 1
深度 2
深度 3
深度 4
深度 5
……

最后画一条曲线:

语言复杂度 ↑ → 算法性能 ↓

看看你的方法在什么地方开始崩溃。


六、而且这和你之前想到的“语义扩散”其实可以接起来

你之前提出过一个想法:

不一定要计算所有词之间的高维向量相似度,而是把相近的词连接起来,然后通过 2 度、3 度关系进行语义扩散。

这个想法和现在这个“基函数”思路其实可以形成一个更大的架构。

可以变成:

                 自然语言
                    ↓
              语言基本单元
                    ↓
          ┌─────────┴─────────┐
          ↓                   ↓
       词/概念节点          操作节点
          ↓                   ↓
      语义关系网络       基本语言函数
          └─────────┬─────────┘
                    ↓
                 组合
                    ↓
                 语义结构
                    ↓
                复杂理解

也就是说,你研究的可能不再是:

“如何让一个神经网络更聪明?”

而是一个更基础的问题:

“自然语言的复杂性,能否由有限数量的语义原子 + 有限数量的组合操作产生?”

这个问题我觉得非常值得认真做实验。

而且如果要验证,我建议下一步直接建立一个 “NLP 基函数最小集合 v0.1”,把每个函数定义成严格的输入、输出和组合规则,然后设计 100~1000 个由简单到复杂的测试句子。这样你的新 NLP 方法就可以和 Transformer/词向量方法做一个非常干净的对照实验。

💬 留言 ⋮⋮

加载中…
💡 不登录也可留言(IP 限制:每文/每天各 1/10 条)

加载中…

分 0.00
纸张白
护眼绿
羊皮卷
夜间黑
100%