All pastes #83196 Raw Edit

naderman

public php v1 · immutable
·published 2006-07-09 13:22 UTC
rendered paste body
	/**	* Splits keywords entered by a user into an array of words stored in $this->split_words	*	* @param string $keywords Contains the keyword as entered by the user	* @param string $terms is either 'all' or 'any'	* @return boolean false if no valid keywords were found and otherwise true	*/	function split_keywords(&$keywords, $terms)	{		global $db, $config, $user;		// $keywords input format: each word seperated by a space, words in a bracket are not seperated		// the user wants to search for any word, convert the search query		if ($terms == 'any')		{			$words = array();			preg_match_all('#([^\s+\-|()]+)[\s+\-|()]#', $keywords, $words);			if (sizeof($words))			{				$keywords = '(' . implode('|', $words) . ')';			}		}		// generate the split_words array shown to the user		$this->split_words = explode(' ', $keywords);		$exact_words = array();		preg_match_all('#([^\s+\-|*()]+)(?:$|[\s+\-|()])#', $keywords, $exact_words);		if (sizeof($exact_words[1]))		{			$exact_words = $exact_words[1];			// start with building a query to retrieve all word ids			$where_sql = array();			foreach ($exact_words as $i => $word)			{				$exact_words[$i] = '\'' . $db->sql_escape($word) . '\'';			}			// we can match exact words with one IN			$sql = 'SELECT word_text, word_id				FROM ' . SEARCH_WORDLIST_TABLE . '				WHERE word_text IN (' . implode(', ', $exact_words) . ')';			$result = $db->sql_query($sql);				// replace text with ids and prefix ids with #			while ($row = $db->sql_fetchrow($result))			{				$words[$row['word_text']] = (int) $row['word_id'];			}			$db->sql_freeresult($result);		}		unset($exact_words);		// now analyse the search query, first split it using the spaces		$query = explode(' ', $keywords);		$this->must_contain_ids = array();		$this->must_not_contain_ids = array();		$this->must_exclude_one_ids = array();		$mode = '';		$ignore_no_id = true;		foreach ($query as $word)		{			// words which should not be included			if ($word[0] == '-')			{				$word = substr($word, 1);				// a group of which at least one may not be in the resulting posts				if ($word[0] == '(')				{					$word = explode('|', substr($word, 1, -1));					$mode = 'exclude_one';				}				// one word which should not be in the resulting posts				else				{					$mode = 'must_not_contain';				}				$ignore_no_id = true;			}			// words which have to be included			else			{				// no prefix is the same as a +prefix				if ($word[0] == '+')				{					$word = substr($word, 1);				}				// a group of words of which at least one word should be in every resulting post				if ($word[0] == '(')				{					$word = explode('|', substr($word, 1, -1));				}				$ignore_no_id = false;				$mode = 'must_contain';			}			// if this is an array of words then retrieve an id for each			if (is_array($word))			{				$id_words = array();				foreach ($word as $i => $word_part)				{					if (isset($words[$word_part]))					{						$id_words[] = $words[$word_part];					}				}				if (sizeof($id_words))				{					$id_words = array_values($id_words);					switch ($mode)					{						case 'exclude_one':							if (sizeof($ids > 1))							{								$this->must_exclude_one_ids[] = $id_words;							}							else							{								$this->must_not_contain_ids[] = $id_words[0];							}						break;						case 'must_contain':							$this->must_contain_ids[] = (sizeof($id_words > 1)) ? $id_words : $id_words[0];						break;					}				}				// throw an error if we shall not ignore unexistant words				else if (!$ignore_no_id)				{					trigger_error(sprintf($user->lang['NO_WORDS'], implode(', ', $word)));				}			}			// else we only need one id			else if (isset($words[$word]))			{				switch ($mode)				{					case 'must_not_contain':						$this->must_not_contain_ids[] = $words[$word];					break;					case 'must_contain':						$this->must_contain_ids[] = $words[$word];					break;				}			}			// throw an error if we shall not ignore unexistant words			else if (!$ignore_no_id)			{				trigger_error(sprintf($user->lang['NO_WORD'], $word));			}		}		// we can't search for negatives only		if (!sizeof($this->must_contain_ids))		{			return false;		}		if (sizeof($this->split_words))		{			$this->split_words = array_values($this->split_words);			return true;		}		return false;	}