加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

PostgreSQL和文字游戏

发布时间:2020-12-13 16:17:37 所属栏目:百科 来源:网络整理
导读:在类似于Ruzzle或Letterpress的文字游戏中,用户必须使用给定的一组字母构造单词: 我将字典保存在一个简单的SQL表中: create table good_words ( word varchar(16) primary key); 由于游戏持续时间非常短,我不想通过调用PHP脚本来检查每个输入的单词,这样可
在类似于Ruzzle或Letterpress的文字游戏中,用户必须使用给定的一组字母构造单词:

我将字典保存在一个简单的SQL表中:

create table good_words (
        word varchar(16) primary key
);

由于游戏持续时间非常短,我不想通过调用PHP脚本来检查每个输入的单词,这样可以在good_words表中查找该单词.

相反,我想在回合开始之前通过一个PHP脚本调用下载所有可能的单词 – 因为所有字母都是已知的.

我的问题是:如果有一种很好的SQL方法可以找到这样的单词吗?

即我可以运行一个较长时间的脚本,将一个列添加到good_words表中,该表将具有与单词columnt相同的字母,但按字母顺序排序…但我仍然无法想出一种方法来匹配它给定一个一组字母.

在PHP脚本内部(与数据库内部)进行单词匹配可能需要太长时间(因为带宽:必须从数据库中获取每一行到PHP脚本).

有什么建议或见解吗?

在CentOS Linux 6.3中使用postgresql-8.4.13.

更新:

我有其他想法:

>创建一个不断运行的脚本(cronjob或守护程序),它会预填充一个带有预编译字母板和可能的单词的SQL表 – 但仍然感觉浪费带宽和CPU,我宁愿在数据库中解决这个问题
>添加整数列a,b,…,z,每当我将一个单词存储到good_words中时,将字母出现在那里.我想知道if it is possible to create an insert trigger in Pl/PgSQL吗?

这可能是一个开始,除了它没有检查我们是否有足够的信件,只有他有正确的字母.
SELECT word from
(select word,generate_series(0,length(word)) as s from good_words) as q
WHERE substring(word,s,1) IN ('t','h','e','l','t','r','s')
GROUP BY word
HAVING count(*)>=length(word);

http://sqlfiddle.com/#!1/2e3a2/3

编辑:

此查询仅选择有效单词,尽管看起来有点多余.它并不完美,但肯定证明它可以做到.

WITH words AS 
(SELECT word,substring(word,1) as sub from
(select word,generate_series(1,'s','o','m','a','d','s'))

SELECT w.word FROM
(
SELECT word,words.sub,count(DISTINCT s) as cnt FROM
(SELECT s,substring(array_to_string(l,''),1) as sub FROM
(SELECT l,generate_subscripts(l,1) as s FROM 
 (SELECT ARRAY['t','s'] as l) 
 as q) 
as q) as let JOIN
words ON let.sub=words.sub
GROUP BY words.word,words.sub) as let
JOIN
(select word,sub,count(*) as cnt from words
 GROUP BY word,sub)
as w ON let.word=w.word AND let.sub=w.sub AND let.cnt>=w.cnt
GROUP BY w.word
HAVING sum(w.cnt)=length(w.word);

为该图像提供所有可能的3个字母单词(485):http://sqlfiddle.com/#!1/2fc66/1
摆弄699个单词,其中485个是正确的:http://sqlfiddle.com/#!1/4f42e/1

编辑2:
我们可以像这样使用数组运算符来获取包含我们想要的字母的单词列表:

SELECT word as sub from
(select word,length(word)) as s from good_words) as q
GROUP BY word
HAVING array_agg(substring(word,1)) <@ ARRAY['t','s'];

所以我们可以用它来缩小我们需要检查的单词列表.

WITH words AS 
(SELECT word,length(word)) as s from 
(
  SELECT word from
(select word,'s']
)as q) as q)
SELECT DISTINCT w.word FROM
(
SELECT word,sub)
as w ON let.word=w.word AND let.sub=w.sub AND let.cnt>=w.cnt
GROUP BY w.word
HAVING sum(w.cnt)=length(w.word) ORDER BY w.word;

http://sqlfiddle.com/#!1/4f42e/44

我们可以使用GIN索引来处理数组,这样我们就可以创建一个表来存储字母数组并使单词指向它(act,cat和tact都指向数组[a,c,t])所以可能这样可以加快速度,但这需要进行测试.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读