PHP MySQL Searching Help :)

Discussion in 'PHP' started by ps3ubo, Apr 15, 2010.

  1. #1
    $search = $_GET[search];

    $result = mysql_query("SELECT * FROM filesearch WHERE page_title LIKE '%".$search."%' OR stripped_cache LIKE '%".$search."%'");

    while($row = mysql_fetch_array($result))
    {
    echo $row['page_title'];
    echo "<br />";
    }


    there the lines from the search, I want it so it searches via keywords instead of trying to find the phrase

    results for "bob marley three little birds"
    = empty

    results for "bob marley - three little birds"
    shows this:
    Bob Marley - Three Little Birds.mp4


    so is it possible to do it by keywords?



    P.S

    HOW DO I MAKE IT ALSO ORDER BY BEST RESULT?
     
    Last edited: Apr 15, 2010
    ps3ubo, Apr 15, 2010 IP
  2. sarahk

    sarahk iTamer Staff

    Messages:
    28,901
    Likes Received:
    4,555
    Best Answers:
    123
    Trophy Points:
    665
    #2
    You need to explode the phrase into individual words, check for "noise" such as "the", "and" as well as the hyphen and remove them.

    this isn't tested but should be pretty much right.
    <?PHP
    $search = $_GET[search];
    
    $bits = removeNoise($search);
    
    $first = true;
    $where = '';
    foreach($bits as $word) 
    {
    	if (!$first) $where .= ' OR ';
    	else $first = false;
    	
    	$where .= "`page_title` LIKE '%{$word}%' 
    			OR `stripped_cache` LIKE '%{.$word}%'";
    }
    $sql = "SELECT * 
    			FROM `filesearch` 
    			WHERE {$where}";
    
    $result = mysql_query();
    
    $output = array();
    while($row = mysql_fetch_array($result))
    {
    	$output[$row['id']]['display'] = $row['page_title'] . '<br />';
    	$output[$row['id']]['score'] = getScore($row['page_title'], $bits);
    }
    
    // http://php.net/manual/en/function.uasort.php
    uasort($output, 'cmp');
    
    foreach($output as $row) echo $row['display'];
    
    
    /**
     * @return integer
     * @param array $a
     * @param array $b
     * @desc used by the uasort
    */
    function cmp($a, $b) {
        if ($a['score'] == $b['score']) {
            return 0;
        }
        return ($a['score'] < $b['score']) ? -1 : 1;
    }	
    
    
    
    /**
     * @return integer
     * @param string $title
     * @param array $words
     * @desc 	loop through the words and generate a score on how well it fits.
    			1 match with a 1 word title would score higher than 1 match with a 5 word title
    			but you need to determine the scoring rules
    
    */
    function getScore($title, $words)
    {
    	return $score;	
    }
    
    /**
     * @return array
     * @param unknown $search
     * @desc 	remove any items from the array that are "noise"
    		 	also need to remove hyphens etc
    */
    function removeNoise($search)
    {
    	$noise = array('and','the','if');
    	$search = str_replace($noise, '', $search);
    	$bits = explode(' ', $search);
    	return $bits;
    }
    ?>
    PHP:
     
    sarahk, Apr 15, 2010 IP
  3. rajamanickam.a

    rajamanickam.a Well-Known Member

    Messages:
    636
    Likes Received:
    5
    Best Answers:
    0
    Trophy Points:
    158
    Digital Goods:
    2
    #3
    will it keep the same query execution time? Or will it create any performance issue?
     
    rajamanickam.a, Apr 16, 2010 IP
  4. sarahk

    sarahk iTamer Staff

    Messages:
    28,901
    Likes Received:
    4,555
    Best Answers:
    123
    Trophy Points:
    665
    #4
    That depends on the size of your database but I suspect that the users download speed will be a bigger bottle neck.

    using like slows things down so changing to = will speed things up
    $where .= "`page_title` = '{$word}' 
    OR `stripped_cache` = '{.$word}'";
    PHP:
    and then you need to check your indexes.

    If its slow on long phrases consider limiting the size of the array holding $bits.
     
    sarahk, Apr 16, 2010 IP
  5. ps3ubo

    ps3ubo Peon

    Messages:
    204
    Likes Received:
    0
    Best Answers:
    0
    Trophy Points:
    0
    #5
    thanks it works good however if i search this:
    hxxp://www . ubo-network . com/ubodevs/mp3source/mediafire.php?search=bob%20marley%20three%20little%20birds
    it shows

    Three 6 Mafia - Lets Plan A Robbery - hopsmp3thing . com.mp3
    Three 6 Mafia Feat Tiesto, Flo Rida, And Sean Kingston - Feel It (FlowAct ivo.C om).mp3
    Three 6 Mafia - Doe Boy Fresh.mp3
    Three 6 Mafia ft. Tiesto, Sean Kingston & Flo-Rida - Feel It (Dj Kweek Remix).mp3
    Three 6 Mafia feat Kalenna - Shake My (Ww .XclusivosBlog.


    then later on in the results it shows

    13. The Sun Is Shining (Bob Marley).mp3
    Bob Marley - No Woman, No Cry (DnB Remix).mp3
    Bob Marley - Jamming.mp3
    Bob Marley - Three Little Birds @ ww w.do ridro .com.mpg
    Bob Marley - Three Little Birds.mp3



    :S
     
    ps3ubo, Apr 16, 2010 IP
  6. VarriaStudios

    VarriaStudios Member

    Messages:
    246
    Likes Received:
    1
    Best Answers:
    0
    Trophy Points:
    28
    #6
    $search = $_GET['search'];

    $search_exploded = explode(" ",$search);
    foreach($search_exploded as $search_each)
    {
    $x++;
    if ($x==1)
    $construct .= "keywords LIKE '%$search_each%'";
    else
    $construct .= "OR keywords LIKE '%$search_each%'";


    }

    }
    $construct = "SELECT * FROM searchengine WHERE $construct";
    $run = mysql_query($construct);

    $foundnum = mysql_num_rows($run);

    if ($foundnum==0)
    echo "no results found.";
    else
    {
    echo "$foundnum results found!<p>";
    while ($runrows = mysql_fetch_assoc($run))
    {
    $title = $runrows['title'];
    $desc = $runrows['description'];
    $url = $runrows['url'];

    echo "
    <b>$title</b><br>
    $desc<br>
    <a href='$url'>$url</a><p>
    ";


    make sure to include 'database.php'; to connect to the database.
     
    VarriaStudios, Apr 16, 2010 IP
  7. sarahk

    sarahk iTamer Staff

    Messages:
    28,901
    Likes Received:
    4,555
    Best Answers:
    123
    Trophy Points:
    665
    #7
    You may need to turn that search into a reverse search by having
    /**
     * @return integer
     * @param array $a
     * @param array $b
     * @desc used by the uasort
    */
    function cmp($a, $b) {
        if ($a['score'] == $b['score']) {
            return 0;
        }
        return ($a['score'] < $b['score']) ? 1 : -1;
    }   
    PHP:
    I've just changed the return values.
     
    sarahk, Apr 16, 2010 IP
  8. ps3ubo

    ps3ubo Peon

    Messages:
    204
    Likes Received:
    0
    Best Answers:
    0
    Trophy Points:
    0
    #8


    Thanks it works great :)
     
    ps3ubo, Apr 17, 2010 IP