问题
I want something similar to Mysql's sorting of data, but in jquery. I have an input and a select tag, like this -
I want the select options to be filtered and sorted depending on the input text's value.
- Filtration OR logic to be applied on the input text and all those options to be kept which contain at least one word
- Sorting/Grouping then sort the remaining options by number of matches, such that options containing all the words as in the input appear at the top, followed by those with one less words and so on. Following is just an illustration and may not be exact -
I am done with the logic of the filtration part. Now comes the sorting part and I am not sure how to do.
Taking an example, say input text posted a string of 5 words. I don't know if there something in jQuery similar to Mysql's order by which can return me the sorted options. So, my logic is like this (pseudocode)-
var numberOfWords;
sortedOptions = new Array();
for(cnt=numberOfWords; cnt>0; cnt --)
{
find options containing exactly those many words
append them to array sortedOptions
}
Now consider the case where numberOfWords = 5 and cnt=3. There are many possible combinations of 3 words, which I need to check to prepare the options with 3 word matches. That's fine but what about the time complexity of the code, when the number of words increases? Is there a better optimized way?
Please note - This checking may need to be done while the user is typing (on every key up) and I can't hit the backend database so frequently. I have not yet found any readymade plugin for the same purpose. Please check my earlier question Any jquery 1.3 compatible plugin to filter dropdown using user text input plus grouping based on number of input strings matched regarding this. If you know any plugin which can solve the problem please post there. But looking forward for a solution to this anyway.
Thanks
回答1:
Something along the lines of this (doesn't completely work):
$(function(){
var $select = $('#mySelectBox'), nonMatches = [], $text = $('#myTextBox').keyup(function(){
// find all the words
var words = $text.val().split(' '), options = []
// nonMatches is an array of <option>s from the prev search that didn't match
// we put them back in the <select>
for (var i in nonMatches)
$select.append(nonMatches[i])
nonMatches = []
// and clear all the old labels like "1 word match"
$select.find('optgroup').each(function(){
var $this = $(this)
$this.replaceWith($this.html())
})
// if the textbox is blank, dont need to search
if (!words.length)
return
// loop thru each <option>
$select.find('option').each(function(){
var wordCount = 0, $this = $(this), html = ' ' + $this.html().toLowerCase() + ' '
// loop thru each word and check if the <select> contains that word
for (var i in words) {
if (html.indexOf(' ' + words[i].toLowerCase() + ' ') > -1)
wordCount++
}
// if this <option> doesn't have any of the words, save and remove it
if (wordCount == 0)
nonMatches.push($this.remove())
else {
// otherwise, save it to be sorted
if (!options[wordCount])
options[wordCount] = []
options[wordCount].push($this.remove())
}
})
// the options array holds all the <option>s that match; we need to sort it
keys = [], sortedOptions = []
for (var i in options) {
keys.push(i)
}
keys.sort()
keys.reverse()
for (var i in keys)
sortedOptions[keys[i]] = options[keys[i]]
for (var i in sortedOptions) {
// put the matches in the <select>
$select.append('<optgroup label="' + (i == words.length ? 'All' : i) + ' word match">')
for (var j in sortedOptions[i]) {
$select.append(sortedOptions[i][j])
}
$select.append('</optgroup')
}
})
})
回答2:
You could filter out the result using array filter. This will give you an array of sub elements.
https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/array/filter
function isBigEnough(element, index, array) {
return (element >= 10);
}
var filtered = [12, 5, 8, 130, 44].filter(isBigEnough);
// filtered is [12, 130, 44]
You could sort by length using the sort function
https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/sort
var numbers = ["aa", "b"];
numbers.sort(function(a, b) {
return a.length - b.length;
});
来源:https://stackoverflow.com/questions/6857969/jquery-logic-to-sort-select-options-by-number-of-word-matches