d3js v5 + Topojson v3 Оптимизация присоединения к csv & json - PullRequest
0 голосов
/ 24 апреля 2018

Для создания карт мне нужно импортировать некоторые значения из csv в json прямо в коде .Для загрузки файлов json и csv я использую асинхронную операцию с объектом Promise и использую два цикла и общий ключ для добавления новых свойств в файл json.

for (var i=0; i< fr[1].length;i++){
        var csvId = fr[1][i].codgeo;
        var csvValue1 = parseFloat(fr[1][i].value1);
        var csvValue0 = parseFloat(fr[1][i].value0);
        for (var j=0; j<topojson.feature(fr[0],fr[0].objects.dep_GEN_WGS84_UTF8).features.length;j++){
          var jsonId = topojson.feature(fr[0],fr[0].objects.dep_GEN_WGS84_UTF8).features[j].properties.codgeo;
          if (csvId === jsonId) {
            topojson.feature(fr[0],fr[0].objects.dep_GEN_WGS84_UTF8).features[j].properties.value1 = csvValue1;
            topojson.feature(fr[0],fr[0].objects.dep_GEN_WGS84_UTF8).features[j].properties.value0 = csvValue0;
            break;

Все работает, но карта отображается наИнтернет требует времени.Есть ли способ оптимизировать время загрузки карты?

Вот пример моего кода: https://plnkr.co/edit/ccwIQzlefAbd53qnjCX9?p=preview

1 Ответ

0 голосов
/ 24 апреля 2018

Я взял ваш plunkr и добавил несколько моментов времени к нему, запустил его несколько раз и получил некоторые данные о том, где ваш сценарий занимает время:

enter image description here

Вот блок с регистрацией.

Я почти уверен, что моя полоса пропускания, где я живу, ниже средней и имеет тонну изменчивости;время загрузки файла показало мне большую изменчивость, вплоть до 500 миллисекунд и до 1800 миллисекунд, все остальное было согласованным

Давайте более подробно рассмотрим этап манипулирования данными, который вы включаете вВаш вопрос:

for (var i=0; i< fr[1].length;i++){
        var csvId = fr[1][i].codgeo;
        var csvValue1 = parseFloat(fr[1][i].value1);
        var csvValue0 = parseFloat(fr[1][i].value0);
        for (var j=0; j<topojson.feature(fr[0],fr[0].objects.dep_GEN_WGS84_UTF8).features.length;j++){
          var jsonId = topojson.feature(fr[0],fr[0].objects.dep_GEN_WGS84_UTF8).features[j].properties.codgeo;
          if (csvId === jsonId) {
            topojson.feature(fr[0],fr[0].objects.dep_GEN_WGS84_UTF8).features[j].properties.value1 = csvValue1;
            topojson.feature(fr[0],fr[0].objects.dep_GEN_WGS84_UTF8).features[j].properties.value0 = csvValue0;
            break;

Вложенный оператор for выполняется примерно 5151 раз по моим подсчетам.Родитель для оператора выполняется 101. Они не должны меняться, так как ваши данные исправлены.Почему эти циклы так долго?Потому что вы вызываете topojson.feature () каждые для итерации:

Если я выделю эту строку:

topojson.feature(fr[0],fr[0].objects.dep_GEN_WGS84_UTF8)

Мы можем видеть, что на самом деле это занимает всего несколько миллисекунд.

Topojson.feature

Возвращает GeoJSON Feature или FeatureCollection для указанного объекта в данной топологии.Если указанным объектом является GeometryCollection, возвращается FeatureCollection, и каждая геометрия в коллекции сопоставляется с Элементом.В противном случае, функция возвращается.Возвращенный объект является поверхностной копией исходного объекта: они могут иметь общие идентификаторы, ограничивающие рамки, свойства и координаты.( из документов ).

Итак, каждый раз, когда мы используем topojson.feature, мы по существу конвертируем топойсон в геойсон.Нам не нужно делать это в цикле for.Давайте сделаем это один раз:

  var featureCollection = topojson.feature(fr[0],fr[0].objects.dep_GEN_WGS84_UTF8);

  //Merge csv & json
  //Add properties from csv to json)
 for (var i=0; i< fr[1].length;i++){
    var csvId = fr[1][i].codgeo;
    var csvValue1 = parseFloat(fr[1][i].value1);
    var csvValue0 = parseFloat(fr[1][i].value0);
    for (var j=0; j<featureCollection.features.length;j++){
      var jsonId = featureCollection.features[j].properties.codgeo;
      if (csvId === jsonId) {
        featureCollection.features[j].properties.value1 = csvValue1;
        featureCollection.features[j].properties.value0 = csvValue0;
        break;
      }
    }
  }

Конечно, мы должны обновить часть кода, которая выполняет рендеринг, чтобы использовать переменную featureCollection, а не topojson

Давайте теперь посмотрим на время: enter image description here

Вот обновленный bl.ock , основанный на приведенном выше, также с точками времени.

Нет, я не забыл указать время для манипуляции, для меня оно составляло в среднем 1,5 миллисекунды.Да, изменчивость в моей полосе пропускания показывает - но время, затрачиваемое на другие манипуляции, должно быть явно меньше независимо от внешних факторов

Дальнейшие улучшения

Предпроектирование геометриисм. вопрос / ответ .

Упрощение геометрии, см. mapshaper.org (хотя я полагаю, что вы уже сделали это).

Удаление ненужных атрибутов из csv или topojson - действительно ли вы используете поле народонаселения в topojson, вам нужны и libgeo, и libgeo_m в topojson (например: "libgeo":"Puy-de-Dôme","libgeo_m":"PUY-DE-DÔME")?

...