首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
社区首页 >问答首页 >PHP:我需要通过用户检查输入字符串中的单词,并根据匹配输出一个响应

PHP:我需要通过用户检查输入字符串中的单词,并根据匹配输出一个响应
EN

Stack Overflow用户
提问于 2010-11-26 13:23:16
回答 1查看 1.9K关注 0票数 1

目前,我有一个非常简单的自动应答/聊天机器人。为了让它发挥更复杂的作用(比如帮助机器人),需要对其进行大量修改。我不是一个php程序员,但我想我知道需要做些什么,经过一些研究,我只是不完全理解在php.net的预匹配和fopen等方面的文章。我知道我可以下载一个现成的帮助机器人,但是我的学习曲线在哪里呢?我也不着急,我喜欢这些小挑战。我在其他地方问过这个问题,那里的人要么什么都不知道,要么根本就不会被打扰--他们只是不停地告诉我下载一个预置的帮助机器人。

任何帮助都是非常感谢的,但是请不要把我送回php手册,因为我已经尝试过使用它了。我需要一个新的方法。

我有一个表单供用户输入一个(最大长度)50个字符文本问题。我认为限制用户可以输入的字符数量将是一种优势,这样就可以更容易地操作字符串。一旦用户提交了问题,它就需要传递给一个变量。

  1. 我想将字符串中的单词与文件中的单词列表进行比较。
  2. 如果文件中不存在单词,则将它们添加到文件中。
  3. 确定某些关键词(如:谁;什么;在哪里;何时;如何;为什么;哪一个)来分解这个问题
  4. 识别任何名词来进一步细分问题(这些名词显然是一个相当大的列表,我必须手动创建)。
  5. 将结果与响应列表(我将手动创建的另一个列表)进行比较。
  6. 输出最佳匹配响应。

下面的代码是基本代码,还没有检查输入字符串中的关键字组合。我已经尽我所能地对代码进行了注释。

以下是我的responder002.php文件:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
/*create the 'question' variable for the users text to be stored in:*/

$question=strtolower($_POST['question']));

/*begin creating the form*/
$ask='<br /><form action="responder002.php" method="POST">Question: <input type="text" name="question">
<input type="submit" value="Ask"></form>';
$answer='<h2>Answer</h2><br />';
/*if the $question variable is empty then ask for input*/
if (empty($question))
{
  print $ask;

  exit;
}
/*otherwise ....*/
else
{

  /*if the variable contains the following strings output to screen the matching response*/
  if ($question=="hello"||$question=="Hello"||$question=="hi"||$question=="Hi"||$question=="G'day"||$question=="hey")
  {
    $answerq="Hello how are you?";
  }
  if ($question=="good"||$question=="good thanks")
  {
    $answerq="Im glad to hear you are good.";
  }
  if ($question=="fine"||$question=="fine thanks") {
    $answerq="Im glad to hear you are fine.";
  }

  echo '<i>You asked me:</i> '.$question.'
    <br />
    <i>I replied:';
  if (empty($answerq)) { 
    echo 'Sorry, I dont know the answer';
  }
  echo '</i>'.$answerq.' '.$ask.;
  exit;
}
echo '</table>';
$h->endpage();
?>
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2010-11-27 14:48:54

这让我想起了很多我在很多月前第一次开始编程时做的事情。只是我一开始就问数学问题。对于初学者来说,编写伊莉莎类型的程序是一项相当大的任务!

显然,你还没有打算写一个获奖的聊天界面,嗯,我希望不是,因为这是一个庞大的研究水平的事业。但是,我将尝试给出一些PHP示例,这些示例将向您展示如何完成您希望执行的几个步骤,并对您所采取的步骤有一点明确性。

一个长教程,准备好你自己.

首先,让我们清理现有的代码。

我假设从该文件的最后一行开始,您正在使用某种类型的HTML生成器,或者试图使用?$h->endpage();,这实际上从未被使用,因为您经常使用exit;,在脚本出现时终止它。您不需要在if块的末尾使用它,除非您希望程序在这一点上结束。程序将在结束大括号}后继续到下一个语句。

我看到您在代码中经常使用echoprintecho是为HTML页编写变量所必需的,但是有更好的方法可以将代码和HTML分开来完成主HTML页面,这样您就可以在这两个页面上都做一个更干净的工作。启动和完成PHP页面<?php ?>的标记可以在页面中的任何地方用于代码的“突破”和“突破”。在括号内,PHP,外部,HTML。

例如:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
<?php
// This is my PHP program

// read the question variable from the Form data
// the form was "post"ed, so we check $_POST
// $_POST is an array (a list) of all the variables sent by the form

$question = strtolower($_POST['question']);

if (empty($question)) {
  // no question, close PHP and start HTML, show the form
?>
<form action="responder002.php" method="POST">
    Question: <input type="text" name="question"> <input type="submit" value="Ask">
</form>
<?php
// back in PHP, if the question was not empty deal with the question
} else {
  // try and find an answer
  if ($question == 'hello' || $question == 'hi') {
    // hello-type question found
    $answerp = "Hello, how are you?";
  } else if ($question == "fine" || $question == "fine thanks") {
    // or a fine-type question
    $answerq = "I am glad to hear you are fine.";
  } else {
    // "else" on its own, no question identified so we do not know
    $answerp = "Sorry, I do not know the answer.";
  }

  // close PHP and display the answer
  // note: opening and closing PHP briefly where we want a variable
  //       using "echo" to output the variable contents
?>
<h2>Answer</h2>

<p><i>You asked me:</i> <?php echo $question; ?></p>
<p><i>I replied:</i> <?php echo $answerp; ?></p>
<?php
  // close the else opening bracket from above
}
// and we are done, close PHP
?>

一旦我们有了接受问题和回答问题的基本方法,我们就可以继续使它更加充实。

你说你想要存储一个已经看过的单词列表,并在新单词出现时继续添加。大概是这样,你可以手动查看被问到的内容并写出新的答案;或者你有其他的动机吗?

无论您存储数据,如果您正在检查数据并将其添加到其中,则它是一个排序的数据库。您可以使用文本文件来存储数据,如果您可以决定一个方法,或者如果数据是复杂的,大多数程序员希望有一个适当的数据库系统,其中包含许多字段的记录可以很容易地存储。

现在,让我们假设您希望使用文本文件。

步骤阶段是决定如何存储单词,我的建议是保持简单的事情是每行一个字。

读取文件的方法有很多种,考虑到我们希望每行只读一个单词,如果使用file()命令,可能是最方便和最简单的方法。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
$words = file("words.txt", FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);

此命令读取整个words.txt,跳过任何空行,不存储任何行尾(文件中的每一行以换行符结尾,将忽略新行选项传递给函数,告诉PHP不要保留这些字符)。

$words现在是文件中每一行的数组,是按它们在文件中出现的顺序排列的列表。

要检查一个单词是否已经在文件中,我们可以使用in_array()函数,我们想知道我们正在检查的单词是否不在文件中。所以我们可以说:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
if (!in_array($currentWord, $words)) {
    // add $currentWord to file
}

!字符的意思是没有。那么,我们如何将这个词添加到文件中呢?还有一个名为file_put_contents()的函数(如果您使用的是比v5更早的PHP版本,那么这个函数就不存在了,请告诉我,我将向您展示更老的更复杂的方法)。file_put_contents()要求我们在每个单词后面加上换行符以结束行,因此我们将"\n"连接到每个单词。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
if (!in_array($currentWord, $words)) {
    file_put_contents("words.txt", $currentWord . "\n", FILE_APPEND | LOCK_EX);
}

标志FILE_APPENDLOCK_EX告诉函数在结束时追加到文件中,而不是从一开始就重新创建文件,并在这样做时独占地锁定文件,这样在我们这样做的时候没有其他人可以写入文件。

对于一个单词,$currentWord,这一切都很好,但是我们如何处理问题中的每个单词呢?

第一步是把问题分成几个字。有几种方法可以做到这一点,但简单的命令是explode()

explode()获取一行或块文本,并使用您指定的分隔符将其拆分到单个片段的列表(数组)中。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
$questionWords = explode(" ", $question);

假设每个单词用空格分隔,这将返回一系列单词。explode()是一个简单的函数,在每一个空格上都是分裂的,所以如果你有两个空格,它就会把它分开,并说在空格之间有一个空字符串。例如,由于双破折号,explode("-", "hello--world") (对空格使用破折号)将给出一个列表('hello', '', 'world')。为了消除空的“单词”,我们可以在爆炸上放置一个过滤器,这样空条目就被删除了。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
$questionWords = array_filter(explode(" ", $question));

现在我们有了问题中的单词列表,我们如何将其与单词文件的读取和新单词的存储结合起来?有一个循环。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
$words = file("words.txt", FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);

$questionWords = array_filter(explode(" ", $question));

foreach ($questionWords as $currentWord) {
    if (!in_array($currentWord, $words)) {
        file_put_contents("words.txt", $currentWord . "\n", FILE_APPEND | LOCK_EX);
    }
}

foreach循环遍历$questionWords中的每个单词,每次通过大括号之间的代码设置变量$currentWord

这是可行的,但效率很低,因为文件必须为每个新单词打开、写入和关闭。最好把新单词列个单子,一次把它们全部加起来。为此,我们创建一个新单词的空数组(列表),并在找到新单词时向其添加新单词。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
$words = file("words.txt", FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);

$questionWords = array_filter(explode(" ", $question));

$newWords = array();
foreach ($questionWords as $currentWord) {
    if (!in_array($currentWord, $words)) {
        // add new word to $newWords
        $newWords[] = $currentWord;
    }
}

// write all the new words at once
file_put_contents("words.txt", implode("\n", $newWords), FILE_APPEND | LOCK_EX);

通过在$newWords中获取列表并执行与explode()相反的操作来同时添加新单词,explode()将一行分解为单个单词,我们将单词列表放到一个文本中,每个单词用换行符"\n"分隔。

我认为这足以暂时接受,仔细阅读,熟悉概念,并让我知道,如果你想继续。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/4288616

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
查看详情【社区公告】 技术创作特训营有奖征文