gpt4 book ai didi

function - Common Lisp : The Remove Function, 它是如何使用的?

转载 作者:行者123 更新时间:2023-12-02 21:54:35 27 4
gpt4 key购买 nike

我有一个“/node/143”形式的查询请求-uri(只是格式的示例)。

我想从字符串中删除第一个正斜杠,我查找了函数 remove并尝试过。我似乎无法让它工作(我在 Linux 上使用 SBCL)。

我已经使用此代码设置了 request-uri。

(setq request-uri "/node/143")

当我检查变量时,我返回了该变量。

request-uri
"/node/143"

我现在尝试删除第一个斜杠(此时只需查看该函数如何正确使用即可)。

(remove "/" request-uri)
"/node/143"

(remove '/ request-uri)
"/node/143"

我什至尝试提供一个列表

(remove '("/") request-uri)
"/node/143"

(remove '('/) request-uri)
"/node/143"

即使字符串是 vectors of characters我想不知何故,也许整个字符串可以放在一个单元格中,我尝试删除整个字符串,但仍然没有运气。

(remove "/node/143" request-uri)
"/node/143"

(remove '/node143 request-uri)
"/node/143"

所以我现在很茫然,这个看似简单的功能真的让我困惑,我以为我完全按照文档进行操作,但没有任何效果。

谁能解释一下这里发生的事情吗?

谢谢。

编辑:我找到了问题的答案,这又引发了另一个问题。

从我使用的字符串中删除元素

(remove #\/ request-uri)

整个字符串怎么样

`(remove #\node request-uri`)

仅适用于第一个字符并抛出错误,以下内容均不执行任何操作。

(remove "node" request-uri)
(remove 'node request-uri)
(remove ?\node request-uri)
(remove #\node request-uri)
(remove '("node") request-uri)

我不确定这里还应该如何解决。

最佳答案

学习阅读 Common Lisp HyperSpec

字符串是 SequencesArrays (一维字符向量)以及 Strings 。这意味着大多数功能都适用。

让我们看看 REMOVE 。 CLHS 给出了这个签名:

remove item sequence &key from-end test test-not start end count key
=> result-sequence

字符串是字符序列。因此,删除的调用将是:

(remove #\/ "/foo/")

或者(例如)

(remove #\/ "/foo/" :start 2)

记住:#\a 是一个字符。 #\node 不是字符。非法的。字符串是“/foo/”

要从字符串中删除的项目必须是字符。没有其他的。为什么?因为默认情况下 TEST 是 EQL,并且 EQL 会将字符串中的字符与项目参数进行比较。另外键默认是 IDENTITY 并且不会更改项目。

如果你的参数是一个字符串怎么办?好吧,那么你必须做更多的事情:

 (remove "/" "/abc/" :key #'string :test #'equal)

这会查看序列中的每个字符并将其放入字符串中。然后,将使用 EQUAL 函数将该字符串与您的项目 "/" 进行比较。这也有效。代价是它需要将“/abc/”的每个字符生成一个字符串,每个字符串都是一个新的对象。

另一种方法是:

 (remove "/" "/abc/" :test (lambda (a b) (eql (aref a 0) b)))

上面在每次测试中检索 "/" 的第一个字符,并将其与字符串 "/abc/" 中的字符进行比较。同样,代价是它需要获取角色五次(在本例中)。

如果你的原始对象是一个字符串,最好的写法是:

(remove (aref "/" 0) "/abc/")

上面我们从字符串 "/" 中获取字符一次,然后 REMOVE 将此字符与字符串中每个字符的默认 EQL 测试进行比较 - 它返回这些字符的新字符串不是 #\/ 的 EQL。

你期望 ?\foo 是什么?在 Common Lisp 中,这是符号 |?fOO|

此外,(remove "foo""afoob") 不起作用,因为字符串(此处为 "foo")不是字符串的元素。请记住,字符是字符串的元素。另请记住,具有诸如 "/" 之类的一项的字符串仍然是字符串而不是字符。因此 "/"#\/ 是不同的类型。第一个是字符串,第二个是字符。

SUBSEQ 从序列中提取序列。这意味着它还从另一个字符串中提取一个字符串:

(subseq "0123456" 1 5)
where 1 is the start and 5 is the end index.

CONCATENATE 附加序列。这意味着它还会附加字符串。

(concatenate 'string "abc" "123")
returns a new string with the strings "abc" and "123" appended.

要删除字符串的一部分,另请参阅函数 STRING-TRIM、STRING-LEFT-TRIM 和 STRING-RIGHT-TRIM。

因此,正如在另一个答案中从字符串中删除子字符串一样,您需要编写一些代码来提取一些字符串,然后连接这些字符串。

SEARCH 在字符串中搜索字符串。

关于function - Common Lisp : The Remove Function, 它是如何使用的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/669407/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com