1

我确定这是我正在犯的一个非常基本的错误,但我无法弄清楚我哪里出错了。

在这个基本的小提琴示例中,你会看到我有 5 个 div。我试图用另一个词替换每个 div 中间的一个词,但它似乎是将第一个 div 的内容复制到所有其他的,正如你从开头的帖子编号中看到的那样。

我用来执行此操作的代码片段是

$('.post').each(function(){
    $('em').html( 
        $('em').html().replace('in','hello')
    );
});

请有人可以帮我看看我哪里出错了?

4

2 回答 2

5

您正在用所有s' 文本 的em内容替换每个文本。还接受一个可以用来引用的函数,或者将当前的 html 作为参数:emhtmlthis

$('.post em').html(function (idx, html){
    return html.replace("in", "hello");
});

您更新的jsFiddle 演示

于 2013-02-14T12:11:02.420 回答
3

没有必要.each- 您可以使用.text带有 mutator 函数并.each在每个匹配元素上进行隐式处理的版本。mutator 函数被传递原始文本,返回值被放回原来的位置:

replaceIn = function() {
    $('.post em').text(function(ix, txt) {
        return txt.replace(/\b(in)\b/g, 'hello');
    });
}

http://jsfiddle.net/alnitak/ZUQ4W/

我使用.text而不是.html因为匹配的元素内没有 HTML。

请注意使用带有/g标志的正则表达式以确保替换所有出现的“in”,并使用\b标记以确保它仅匹配整个单词。

的字符串版本replace只能替换字符串中的第一个匹配项。当然,如果这是您的意图,请随意使用它!

另请注意,如果您在具有后代的元素上使用 this(或变体 using ),则必须非常小心.html,因为外部元素在内部元素之前被处理,并且对外部元素的操作可能会对后代产生意外的更改。明智地选择您的选择器,以便只更改叶节点!

避免的另一个很好的理由.html()是,如果您序列化一个元素,然后再次反序列化它,.html()那么已在该元素上设置的任何属性或事件都将丢失。尽可能在使用 HTML 字符串操作的情况下对 DOM 进行更改!

为了安全起见,请使用以下命令:

replaceIn = function () {
    $('.post em').contents().filter(function () {
        return this.nodeType === 3;
    }).each(function() {
        // NB: DOM level 3 uses .textContent in preference to .nodeValue
        this.nodeValue = this.nodeValue.replace(/\b(in)\b/g, 'hello');
    });
}

这绝对确保index不能修改任何嵌套元素(例如标签!)。

http://jsfiddle.net/alnitak/rZU5d/

于 2013-02-14T12:15:24.953 回答