高亮显示重复的行值JavaScript

时间:2018-09-11 11:57:09

标签: javascript jquery arrays string dom

我正在使用JS突出显示表中的重复值。

代码的基本作用是在数组中添加表行值,然后比较它是否存在,然后突出显示该行。

该代码运行正常,但突出显示了所有相同颜色(红色)的重复值。我需要做的是用不同的颜色突出显示每组相似的值。可以说我有4组重复值,每组应以不同的颜色突出显示。可能需要随机生成颜色,因为表中可能有多个重复值。

 $(function() {
    var tableRows = $("#sortable tbody tr"); //find all the rows
    var rowValues = []; //to keep track of which values appear more than once
    tableRows.each(function() { 
        var rowValue = $(this).find(".content").html();
        if (!rowValues[rowValue]) {
            var rowComposite = new Object();
            rowComposite.count = 1;
            rowComposite.row = this;
            rowValues[rowValue] = rowComposite;
        } else {
            var rowComposite = rowValues[rowValue];
            if (rowComposite.count == 1) {
                $(rowComposite.row).css('backgroundColor', 'red');
            }
            $(this).css('backgroundColor', 'red');
            rowComposite.count++;
        }
    });
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<table id="sortable">
    <tbody>
        <tr>
            <td class="content">A</td>
        </tr>
        <tr>
            <td class="content">B</td>
        </tr>
        <tr>
            <td class="content">A</td>
        </tr>
         <tr>
            <td class="content">C</td>
        </tr>
         <tr>
            <td class="content">C</td>
        </tr>
    </tbody>
</table>

6 个答案:

答案 0 :(得分:2)

最好不要使用array来代替rowValues,而可以使用object来检查key值的存在。

您还可以使用array种颜色,从中获取动态颜色,并在每次发现新值时不断移动array,因此每个不同的值都将具有其相关的不同颜色。

并且不需要检查count块中的else,因为只要您到达此块,就意味着此value已经存在于array中。

这应该是您的代码:

$(function() {
  var tableRows = $("#sortable tbody tr"); //find all the rows
  var colors = ["red", "blue", "green", "yellow", "#f5b"];
  var rowValues = {};
  tableRows.each(function() {
    var rowValue = $(this).find(".content").html();
    if (!rowValues[rowValue]) {
      var rowComposite = new Object();
      rowComposite.count = 1;
      rowComposite.row = this;
      rowValues[rowValue] = rowComposite;
    } else {
      var rowComposite = rowValues[rowValue];
      if (!rowComposite.color) {
        rowComposite.color = colors.shift();
      }
      rowComposite.count++;
      $(this).css('backgroundColor', rowComposite.color);
      $(rowComposite.row).css('backgroundColor', rowComposite.color);
    }
  });
});

演示:

$(function() {
  var tableRows = $("#sortable tbody tr"); //find all the rows
  var colors = ["red", "blue", "green", "yellow", "#f5b"];
  var rowValues = {};
  tableRows.each(function() {
    var rowValue = $(this).find(".content").html();
    if (!rowValues[rowValue]) {
      var rowComposite = new Object();
      rowComposite.count = 1;
      rowComposite.row = this;
      rowComposite.color = colors.shift();
      rowValues[rowValue] = rowComposite;
    } else {
      var rowComposite = rowValues[rowValue];
      rowComposite.count++;
      $(this).css('backgroundColor', rowComposite.color);
      $(rowComposite.row).css('backgroundColor', rowComposite.color);
    }
  });
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<table id="sortable">
  <tbody>
    <tr>
      <td class="content">A</td>
    </tr>
    <tr>
      <td class="content">B</td>
    </tr>
    <tr>
      <td class="content">A</td>
    </tr>
    <tr>
      <td class="content">C</td>
    </tr>
    <tr>
      <td class="content">C</td>
    </tr>
  </tbody>
</table>

答案 1 :(得分:1)

我将为每个具有相同内容的单元格的内容文本创建一个数组。一旦有了它,就可以对其进行迭代并根据需要突出显示单元格。

要生成随机颜色,我添加了一种方法,该方法具有一个Set来跟踪生成的颜色。它将检查之前是否已生成随机的生成器颜色,并一直生成颜色,直到生成唯一的颜色为止。

您可能会选择使文本难以辨认的颜色,或者两种对比度不足以区分它们的随机颜色。因此,这不是一个完美的解决方案。

function generateRandomInt(max, min = 0) {
  return Math.floor(Math.random() * (max - min + 1) + min);
}

/**
 * This method will return a new method, when the returned method is 
 * called it will return a unique color. Subsequent calls to the color
 * generator will never return the same color.
 */
function colorGenerator() {
  // Create a Set at the function scope which we can use to keep
  // track of the colors generated by the returned method.
  const
    generatedColors = new Set();
    
  return () => {
    let randomColor;
    // Keep generating a random color in the format "rgb(R,G,B)" until 
    // a color is generated that doesn't yet exist in the set. This doesn't
    // take into account that at some point you'll run out of 
    // possible colors (but it will take 16M+ tries).
    do {
      randomColor = `rgb(${generateRandomInt(255)},${generateRandomInt(255)},${generateRandomInt(255)})`;
    } while (generatedColors.has(randomColor));
    
    // Add the generated, unique, color to the set.
    generatedColors.add(randomColor);
    
    // Return the random color.
    return randomColor;  
  };
}

function highlightDoubles(table) {
  const
    // Get all the element with the content CSS class.
    contentCells = table.querySelectorAll('.content'),
    // Create map, the cell content will be the key and the value will be
    // an array with cells that have the key as content.
    contentMap = new Map();
   
  // IE doesn't support forEach on a NodeList, convert it to an array first.
  Array.from(contentCells).forEach(cell => {
    const
      // For each cell check if the content has been encountered before. If so
      // return the map value and else create a new array.
      array = (contentMap.has(cell.textContent))
        ? contentMap.get(cell.textContent)
        : [];
      // Push the current cell into the array.
      array.push(cell)
      // Store the array in the map.
      contentMap.set(cell.textContent, array);
  });

  // Create a color generator, it will create a random
  // color but never the same color twice.
  const 
    randomColor = colorGenerator();
    
  // Iterate over all the entries in the map, each entry is a unique 
  // cell content text
  contentMap.forEach(cells => {
    // When the lengths of the cells array is less than 2 it means 
    // it is not multiple times in the table. Exit now.
    if (cells.length < 2) {
      return;
    }
    
    // Generate a random color for the current content text. This is just
    // a very naive implementation. It doesn't make any promises on readability.
    const
      color = randomColor();
      
    // Apply the random color to all the cells with the same content.
    cells.forEach(cell => {
      cell.style.backgroundColor = color;
    });
  });
}

highlightDoubles(document.getElementById('sortable'));
<table id="sortable">
    <tbody>
        <tr>
            <td class="content">A</td>
        </tr>
        <tr>
            <td class="content">B</td>
        </tr>
        <tr>
            <td class="content">A</td>
        </tr>
         <tr>
            <td class="content">C</td>
        </tr>
         <tr>
            <td class="content">C</td>
        </tr>
    </tbody>
</table>

答案 2 :(得分:0)

无论何时在if语句中创建新对象,都要做类似的事情

var rowComposite = new Object();
rowComposite.count = 1;
rowComposite.row = this;
var myColor = generateRandomColor();
rowComposite.color = myColor;

然后在分配颜色时,将其分配为.color而不是'red':

$(rowComposite.row).css('backgroundColor', rowComposite.color);

您可以在这里了解有关js随机颜色生成的信息:this

答案 3 :(得分:0)

您可以使用以下自定义函数示例生成随机颜色

$(function() {
    var tableRows = $("#sortable tbody tr"); //find all the rows
    var rowValues = []; //to keep track of which values appear more than once
    tableRows.each(function() { 
        var rowValue = $(this).find(".content").html();
        if (!rowValues[rowValue]) {
            var rowComposite = new Object();
            rowComposite.count = 1;
            rowComposite.row = this;
            rowValues[rowValue] = rowComposite;
        } else {
            var rowComposite = rowValues[rowValue];
            if (rowComposite.count == 1) {
                $(rowComposite.row).css('backgroundColor',getRandomColor());
            }
           // $(this).css('backgroundColor', getRandomColor());
           $(this).css('backgroundColor', 'red');
            rowComposite.count++;
        }
    });
});

function getRandomColor() {
  var letters = '0123456789ABCDEF';
  var color = '#';
  for (var i = 0; i < 6; i++) {
    color += letters[Math.floor(Math.random() * 16)];
  }
  return color;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<table id="sortable">
    <tbody>
        <tr>
            <td class="content">A</td>
        </tr>
        <tr>
            <td class="content">B</td>
        </tr>
        <tr>
            <td class="content">A</td>
        </tr>
         <tr>
            <td class="content">C</td>
        </tr>
         <tr>
            <td class="content">C</td>
        </tr>
        <tr>
            <td class="content">C</td>
        </tr>
    </tbody>
</table>

答案 4 :(得分:0)

function random_rgba() {
    var o = Math.round, r = Math.random, s = 255;
    return 'rgba(' + o(r()*s) + ',' + o(r()*s) + ',' + o(r()*s) + ',' + r().toFixed(1) + ')';
}

$(function() {

    var tableRows = $("#sortable tbody tr"); //find all the rows
    var rowValues =  {}; //to keep track of which values appear more than once
    var color = "";
    tableRows.each(function() { 
        var rowValue = $(this).find(".content").html();
        if (rowValues[rowValue]){
            color = rowValues[rowValue];
        }else{
            color = random_rgba();
          rowValues[rowValue] = color;
        }
        $(this).css('backgroundColor', color);
    });
});

在这里工作:https://jsfiddle.net/zn0g9u34/9/

答案 5 :(得分:0)

您可以尝试一下。简单而时尚:

$(function(){
    var st=document.createElement("style");
    document.head.appendChild(st);
    var sty={}, s;
    var A={}, cou=1;
    $("#sortable .content").each(function(i, c){
         if(!sty[c.innerHTML]){
            sty[c.innerHTML]=1;
            A[c.innerHTML]=cou++;
         }else sty[c.innerHTML]+=1;
         c.setAttribute("data-w", A[c.innerHTML]);
    });
    for(s in sty){
        if(sty[s]>1){
            st.sheet.insertRule("#sortable .content[data-w='"+A[s]+"']{background-color:rgb("+
                parseInt(Math.random()*256)+","+ 
                parseInt(Math.random()*256)+","+
                parseInt(Math.random()*256)+
            ");}", 0);
        };
    };
});

打扰了,我正在用手机打字,我无法拨弄小提琴。


Try it online!