简体   繁体   English

Javascript字符串匹配模式帮助

[英]Javascript string matching pattern help

i need to find few words or matching pattern using a Javascript. 我需要使用Javascript找到几个单词或匹配模式。

this is the requirement. 这是要求。

i have a string like this, 我有一个像这样的字符串,

Here is a quick guide for the next time you reach for your favorite oil and some other topics 这是下次您喜欢的石油和其他主题的快速指南

and i need to match this string against a string like this 我需要将此字符串与这样的字符串匹配

favorite oil and some other topics can be based on something blah blah

how do i get the intersection of matching text blocks? 我如何获得匹配的文本块的交集?

I already tried intersect Javascript script function, for some strings it's not working properly. 我已经尝试了相交的Javascript脚本函数,对于某些字符串,它无法正常工作。

How to solve this problem? 如何解决这个问题呢? can this be done using Regex? 这可以使用Regex完成吗?

Please advice. 请指教。

You have to find the Longest common substring . 你必须找到最长的公共子串

If the strings are not very long, I recommend using Tim's approach. 如果琴弦不长,我推荐使用Tim的方法。 Otherwise, this is a Javascript implementation of the Longest common substring algorithm with dynamic programming. 否则,这是具有动态编程的最长公共子串算法的Javascript实现。 The runtime is O(mn) where m and n are the lengths of the 2 strings respectively. 运行时为O(mn),其中m和n分别是2个字符串的长度。

An example usage: 示例用法:

var first = "Here is a quick guide for the next time you reach for your favorite oil and some other topics";
var second = "favorite oil and some other topics can be based on something blah blah";

console.log(first.intersection(second)); // ["favorite oil and some other topic"]

This is the algorithm implementation. 这是算法实现。 It returns an array of the longest common substring(s). 它返回最长公共子串的数组。 Extended the native String class, so the intersect method is available on all strings. 扩展了本机String类,因此所有字符串都可以使用intersect方法。

String.prototype.intersection = function(anotherString) {
    var grid = createGrid(this.length, anotherString.length);
    var longestSoFar = 0;
    var matches = [];

    for(var i = 0; i < this.length; i++) {
        for(var j = 0; j < anotherString.length; j++) {
            if(this.charAt(i) == anotherString.charAt(j)) {
                if(i == 0 || j == 0) {
                    grid[i][j] = 1;
                }
                else {
                    grid[i][j] = grid[i-1][j-1] + 1;
                }
                if(grid[i][j] > longestSoFar) {
                    longestSoFar = grid[i][j];
                    matches = [];
                }
                if(grid[i][j] == longestSoFar) {
                    var match = this.substring(i - longestSoFar + 1, i);
                    matches.push(match);
                }
            }
        }
    }
    return matches;
}

Also need this helper function to create a 2d array with all elements initialize to 0. 还需要此辅助函数来创建一个所有元素初始化为0的二维数组。

// create a 2d array
function createGrid(rows, columns) {
    var grid = new Array(rows);
    for(var i = 0; i < rows; i++) {
        grid[i] = new Array(columns);
        for(var j = 0; j < columns; j++) {
            grid[i][j] = 0;
        }
    }
    return grid;
}

This isn't very efficient and there are much better ways to do this in general (see @Anurag's answer), but it's simple and works fine for short strings: 这不是很有效,并且有更好的方法来执行此操作(请参阅@ Anurag的答案),但它很简单,适用于短字符串:

function stringIntersection(str1, str2) {
    var strTemp;

    // Swap parameters if necessary to ensure str1 is the shorter
    if (str1.length > str2.length) {
        strTemp = str1;
        str1 = str2;
        str2 = strTemp;
    }

    // Start with the whole of str1 and try shorter substrings until
    // we have a common one
    var str1Len = str1.length, l = str1Len, start, substring;
    while (l > 0) {
        start = str1Len - l;
        while (start >= 0) {
            substring = str1.slice(start, l);
            if (str2.indexOf(substring) > -1) {
                return substring;
            }
            start--;
        }
        l--;
    }
    return "";
}

var s1 = "Here is a quick guide for the next time you reach"
       + " for your favorite oil and some other topics";
var s2 = "favorite oil and some other topics can be based on"
       + " something blah blah";

alert( stringIntersection(s1, s2) );

A simple polyfill of filter a string 一个简单的polyfill过滤字符串

if (!String.prototype.intersection) {
  String.prototype.intersection = function(anotherString, caseInsensitive = false) {
    const value = (caseInsensitive) ? this.toLowerCase()          : this;
    const comp  = (caseInsensitive) ? anotherString.toLowerCase() : anotherString;
    const ruleArray = comp.split("").reduce((m,v) => {m[v]=true; return m;} ,{})
    return this.split("").filter( (c, i) => ruleArray[value[i]] ).join("")
  }
}

"HelloWorld".intersection("HEWOLRLLODo", true) “HelloWorld”.intersection(“HEWOLRLLODo”,true)

"HelloWorld" - case insensitive “HelloWorld” - 不区分大小写

"HelloWorld".intersection("HEWOLRLLODo") “HelloWorld” 的.intersection( “HEWOLRLLODo”)

"HoWo" - case sensitive “HoWo” - 区分大小写

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM