来自数据库

时间:2016-02-13 23:55:02

标签: php mysql

我一直在谷歌搜索并搜索,但我仍然找不到答案。

所以我的问题是我想从mySQL数据库中提取当前在页面上显示的id的相关内容。在数据库中,我有一个专门用于关键字的列,我使用LIKE查询来根据这些关键字提取id。但是,我只获得一个id,因为LIKE查询按字面意思查看关键字。例如,keyword1 ='apples berries oranges'与keywords2 ='apples'' berries''oranges'不同。我想要后者,所以它可以提取更多相关数据。

我也认为我可能会接近这个错误,但我不知道有任何其他方式来提取相关项目。

这是我的代码......

<?php
            include 'data/data_connect.php';

            if ($sugg_qs = $db->query("SELECT * FROM questions WHERE keywords LIKE '$keywords' LIMIT 4")) {
                if ($q_count = $sugg_qs->num_rows) {
                    echo $q_count;
                        while($row = $sugg_qs->fetch_assoc()) {
                            echo $row->title;
                        }
                            $sugg_qs->free();
                        } else {
                            die('error');
                        }
                } else {
                    die('error');
            }
        ?>

更新

if ($sugg_qs = $db->query("SELECT * FROM questions WHERE keywords LIKE CONCAT('%', '$keywords' ,'%') LIMIT 3")) {
                if ($q_count = $sugg_qs->num_rows) {
                    $row = $sugg_qs->fetch_all(MYSQLI_ASSOC);
                    foreach ($row as $rows) {
                        echo $rows['title'];
                    }
                } else {
                    die('error');
            }

此代码适用于只有一个关键字的id。所以我猜一个可能的(但不受欢迎的)解决方案是为每个新关键字创建一个新列,并为每个关键字使用LIKE。

有没有办法避免创建更多列?

感谢那些已经帮助过的人:)

最终更新? 好。所以我用最可能的方式来编写代码,但显然它对我有用。所以首先我将表格标准化,其中每个元素仅限于5个关键字和1个类别。因此,在查询中,我调用具有相似关键字的项目,如果没有类似的结果,则我从原始项目中调用相同类别的项目。

这是寻找解决方案的那些(杂乱)代码!

$q_kw_arr = explode(' ', $keywords);

            if ($sugg_qs = $db->query("SELECT keywords, category, title FROM questions WHERE keywords LIKE CONCAT('%', '$q_kw_arr[0]' ,'%') OR CONCAT('%', '$q_kw_arr[1]' ,'%') OR CONCAT('%', '$q_kw_arr[2]' ,'%') OR CONCAT('%', '$q_kw_arr[3]' ,'%') OR CONCAT('%', '$q_kw_arr[4]' ,'%') OR category= '$category' LIMIT 4")) {
                if ($q_count = $sugg_qs->num_rows) {
                    $row = $sugg_qs->fetch_all(MYSQLI_ASSOC);
                    foreach ($row as $rows) {
                        echo $rows['title'];
                    }
                } else {
                    echo 'error';
                    }
            }

特别感谢..

Terminus,Grzegorz J和infidelsawyer

2 个答案:

答案 0 :(得分:1)

您可能需要检查一下$keywords变量中是否有任何关键字,但这是一个适用于您当前结构的解决方案。

假设字符串中的每个关键字用空格分隔:

$keywordSeparator = " ";
$keywords = explode($keywordSeparator, $keywords);
$keywordsWhere = " WHERE keywords LIKE '%" . implode("%' OR keywords LIKE '%", $keywords) . "%'";

$query = "SELECT *
FROM questions 
" . $keywordsWhere;

if ($sugg_qs = $db->query($query)) {

修改

Paul Spiegel发表了一些好评(不只是在我的代码中指出了错误:)。

如果要避免对关键字进行部分匹配,则应将所有关键字包装在分隔符中。

为避免apple匹配appliepie,您可以在关键字周围存储空格。因此apple oranges变为apple oranges。搜索这些关键字的行为是WHERE keywords LIKE '% apple %' OR keywords LIKE '% oranges %'

但是,此时,如果将关键字存储在自己的表中,每行一个关键字,则应该会看到性能改进。修改后的questions表和下面的新question_keywords表的示例表结构:

--
-- Table structure for table `questions`
--
CREATE TABLE IF NOT EXISTS `questions` (
`question_id` int(11) NOT NULL AUTO_INCREMENT,
  `title` varchar(254) NOT NULL,
  PRIMARY KEY (`question_id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=1 ;

--
-- Table structure for table `question_keywords`
--
CREATE TABLE IF NOT EXISTS `question_keywords` (
`keyword_id` int(11) NOT NULL AUTO_INCREMENT,
  `question_id` int(11) NOT NULL,
  `keyword` varchar(50) NOT NULL,
  PRIMARY KEY (`keyword_id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=1 ;
--
-- Indexes for table `question_keywords`
--
ALTER TABLE `question_keywords`
 ADD KEY `question_id_keyword` (`question_id`,`keyword`);

一些示例数据

INSERT INTO `questions` (`title`) VALUES ('Question #1'), ('Question #2'), ('Question #3');

INSERT INTO `question_keywords` (`question_id`, `keyword`)
VALUES
    (1, 'apple')
    ,(2, 'orange')
    ,(3, 'ILikeFruit')
    ,(3, 'banana')
    ,(3, 'grape')
    ,(3, 'apple');

然后你可以像这样搜索

$keywordSeparator = " ";
$keywords = explode($keywordSeparator, $keywords);
$keywordsAnd = "'" . implode("','", $keywords) . "'";

$query = "
  SELECT DISTINCT q.*
  FROM questions q
  INNER JOIN question_keywords k
    ON q.question_id = k.question_id
    AND k.keyword IN (" . $keywordsAnd . ")";

if ($sugg_qs = $db->query($query)) {

搜索可能看起来更复杂,因为我们现在需要JOIN,但它应该加速,因为它不必使用%进行搜索,并且可以利用我们对{的索引{1}}栏。

答案 1 :(得分:0)

你可以尝试:

if ($sugg_qs = $db->query("SELECT * FROM questions WHERE keywords LIKE CONCAT('%', $keywords ,'%') LIMIT 4")) {