Объединение параллельных массивов в один массив объектов и сортировка - PullRequest
1 голос
/ 17 марта 2020

У меня есть таблица входов с заголовками: внутреннее измерение, внешнее измерение и количество. Пользователь может ввести до 20 разных экземпляров. Например, пользовательские данные:

Строка 1 - ID = 20, OD = 30, QTY = 6
Строка 2 - ID = 10, OD = 15, QTY = 3
Строка 3 - ID = 40, OD = 52, QTY = 15
et c ...

В настоящее время я собираю все идентификаторы, OD и QTY в параллельные массивы, поэтому для этого примера:

IDarray = [20, 10, 40, et c ...]
ODarray = [30, 15, 52, et c ...]
QTYarray = [6, 3, 15, et c ...]

У меня есть al oop, который проходит через таблицу и игнорирует любые пустые входные данные при построении этих массивов. Все это работает нормально, но я хочу иметь возможность сортировать их от самых больших до самых маленьких на основе внешнего диаметра (OD). Похоже, что лучший способ сделать это - объединить 3 параллельных массива в массив объектов, содержащий все три элемента, но я не могу найти руководство по созданию массива объектов, когда входные значения могут постоянно другой. Я уверен, что это очень просто c, но я новичок в кодировании javascript, поэтому я борюсь с этим.

Я прикрепил фрагмент своего кода, но я сократил его до 3 входов для экономии места.

<script>

window.onload = function() {
$("#unit1").val(default_unit);
$("#unit2").val(default_unit);
$("#unit3").val(default_unit);


function myFunction() {

var unit1 = document.getElementById("unit1").value;
var unit2 = document.getElementById("unit2").value;
var unit3 = document.getElementById("unit3").value;


var id1 = (unit1 == 1) ? document.getElementById("id1").value:document.getElementById("id1").value / 25.4;
var id2 = (unit2 == 1) ? document.getElementById("id2").value:document.getElementById("id2").value / 25.4;
var id3 = (unit3 == 1) ? document.getElementById("id3").value:document.getElementById("id3").value / 25.4;

var od1 = (unit1 == 1) ? document.getElementById("od1").value:document.getElementById("od1").value / 25.4;
var od2 = (unit2 == 1) ? document.getElementById("od2").value:document.getElementById("od2").value / 25.4;
var od3 = (unit3 == 1) ? document.getElementById("od3").value:document.getElementById("od3").value / 25.4;

var qty1 = document.getElementById("qty1").value;
var qty2 = document.getElementById("qty2").value;
var qty3 = document.getElementById("qty3").value;

Array.prototype.clean = function(deleteValue) {
    for (var i = 0; i < this.length; i++) {
        if (this[i] == deleteValue) {         
            this.splice(i, 1);
            i--;
        }
    }
    return this;
};

var id_values = [id1, id2, id3].clean("");
var od_values = [od1, od2, od3].clean("");
var qty_values = [qty1, qty2, qty3].clean("");               
alert(id_values);
alert(od_values);
alert(qty_values);


//var testObject = {
//  id_values,
//  od_values, <--sort by this
//  qty_values;
//};
}
</script>
<table class="inputstable">
    <tr>
        <th>Unit</th>
        <th>Inside Dimension</th>
        <th>Outside Dimension</th>
        <th>Quantity</th>
    </tr>
    <tr>
        <td><select class="custom_select" id="unit1">
            <option value=1>in</option>
            <option value=2>mm</option>
        </td>
        <td><input class="custom_input" type="text" id="id1"></td>
        <td><input class="custom_input" type="text" id="od1"></td>
        <td><input class="custom_input" type="number" id="qty1"></td>
    </tr>
    <tr>
        <td><select class="custom_select" id="unit2">
            <option value=1>in</option>
            <option value=2>mm</option>
        </td>
        <td><input class="custom_input" type="text" id="id2"></td>
        <td><input class="custom_input" type="text" id="od2"></td>
        <td><input class="custom_input" type="number" id="qty2"></td>
    </tr>
    <tr>
        <td><select class="custom_select" id="unit3">
            <option value=1>in</option>
            <option value=2>mm</option>
        </td>
        <td><input class="custom_input" type="text" id="id3"></td>
        <td><input class="custom_input" type="text" id="od3"></td>
        <td><input class="custom_input" type="number" id="qty3"></td>
    </tr>

<button class="special_button" onclick="myFunction()">Tester</button>

Спасибо!

1 Ответ

0 голосов
/ 18 марта 2020

Из того, что я понимаю, вы получите три массива. Эти массивы будут иметь одинаковую длину с индексом, представляющим, какой строкой в ​​таблице они являются. Вам нужно отсортировать индексы всех трех массивов на основе значений одного. Это означает, что вам необходимо убедиться, что при перемещении значения в одном массиве значения всех других массивов перемещаются одинаково.

К сожалению, я не знаю, как это сделать с нативными функциями. Вы должны были бы реализовать сортировку самостоятельно, чтобы управлять этим способом.

Во внешнем интерфейсе лучше иметь связанные данные, структурированные как массив объектов, а не как набор связанных табличных массивов. Таким образом, вы можете более интуитивно выполнять сортировку, поиск, фильтры и т. Д. c. Давайте go о том, как это сделать.

Я буду использовать ваш тестовый объект:

var testObject = {
  id_values: [20, 10, 40],
  od_values: [30, 15, 2],
  qty_values: [6, 3, 15]
};

Чтобы преобразовать связанные массивы в массив объектов, содержащих связанные данные, я создам экземпляр массива с нулевым заполнением с тем же номером индексов в виде таблиц. Затем мы сопоставляем этот пустой массив, создавая объект из данных в каждой таблице:

const dataArray = new Array(obj[by].length).fill(0).map((_, i) => {
  return {
    id_values: testObject.id_values[i],
    od_values: testObject.od_values[i],
    qty_values: testObject.qty_values[i]
  }
}) .sort((a, b) => a[by] > b[by])

На этом этапе таблицы будут преобразованы в более JavaScript дружественный массив объектов, который будет выглядеть следующим образом:

const dataArray = [ 
  { id_values: 20, od_values: 30, qty_values: 6 },  
  { id_values: 10, od_values: 15, qty_values: 3 },  
  { id_values: 40, od_values: 2, qty_values: 15 } 
]

Теперь ТО можно легко отсортировать с помощью собственной сортировки массива:

dataArray.sort((a, b) => a.od_values > b.od_values)

, что приведет к сортировке!

const sortedData = [ 
  { id_values: 40, od_values: 2, qty_values: 15 },  
  { id_values: 10, od_values: 15, qty_values: 3 },  
  { id_values: 20, od_values: 30, qty_values: 6 } 
]

Значения могут быть деструктурированы в связанные таблицы путем сокращения массива объектов:

dataArray.reduce((acc, el) => {
  Object.keys(el).map(col => {
    acc[col].push(el[col])
  })
  return acc
}, {
  id_values: [],
  od_values: [],
  qty_values: []
})

Получается исходная структура данных, но сортируется по выбранному атрибуту:

const sortedArrays = { 
  id_values: [ 40, 10, 20 ],  
  od_values: [ 2, 15, 30 ],  
  qty_values: [ 15, 3, 6 ] 
}

Собираем все вместе:

var testObject = {
  id_values: [20, 10, 40],
  od_values: [30, 15, 2],
  qty_values: [6, 3, 15]
};

const sortTableObj = (obj, by) => {
  const dataArray = new Array(obj[by].length).fill(0).map((_, i) => {
    return {
      id_values: testObject.id_values[i],
      od_values: testObject.od_values[i],
      qty_values: testObject.qty_values[i]
    }
  }).sort((a, b) => a[by] > b[by])
  console.log('dataArray: ', dataArray) 

  return dataArray.reduce((acc, el) => {
    Object.keys(el).map(col => {
      acc[col].push(el[col])
    })
    return acc
  }, {
    id_values: [],
    od_values: [],
    qty_values: []
  })
}

sortTableObj(testObject, 'od_values')

Дайте мне знать, если у вас есть какие-либо вопросы!

...