Страницы

Поиск по вопросам

Показаны сообщения с ярлыком index. Показать все сообщения
Показаны сообщения с ярлыком index. Показать все сообщения

воскресенье, 15 марта 2020 г.

Обращение к объекту, как к массиву

#javascript #объекты #index

Есть ли простой способ обратиться к ключу объекта по его индексу? Может в Underscore
есть магические методы?

Вопрос возник на фоне такой задачи. Есть объект:

plane: {
    432: {
        columns: {
            543: {
                name: 'lolo'
            },
            984: {
                name: 'lala'
            },
            ...
        }
    },
    ...
}


Где среди n-го количества plane, и n-го количества column нужно выбрать первый plane
и первый column внутри него.

Как сделать это проще всего?
    


Ответы

Ответ 1



Хотя ES6 обеспечивает определённый порядок ключей при обходе, гораздо правильнее и удобнее использовать массив, положив тот ключ внутрь объекта, например, в поле id. Но если уж очень хочется, то можно сделать так (как-нибудь сократив название): Object.prototype.getByKeyIndex = function (i) { var key = Object.keys(this)[i]; return key && this[key]; } Тогда на объекте из вопроса будет такое: plane.getByKeyIndex(0).columns.getByKeyIndex(1).name // "lala" Вроде, более-менее нормально выглядит. Ключ сохраняется в переменную и проверяется, чтобы в таком варианте получилось undefined: ({ undefined: 42 }).getByKeyIndex(256) Я новичок и хочу у Вас спросить - хорошо ли изменять прототип нативных объектов? Что будет если я добавлю метод, а после кто-то другой тоже Ваш ответ увидит и решит добавить свой, но с таким же методом? В большинстве случаев изменять прототип Object'а не очень хорошо. Но для защиты от прототипных свойств принято фильтровать for-in через hasOwnProperty. Другой вариант - добавлять в прототип не так, как это сделал я, а через скрытое свойство, чтобы оно не перебиралось. Если двое добавили одинаковое свойство, то одно из них перезапишет другое. По идее, последнее добавленное должно перезаписать предыдущее, но можно пошаманить с readonly, чтобы осталось более раннее. В любом случае, такая ситуация заведомо плохая и лучше в неё не попадать. Если двое добавят одну и ту же функцию под разными именами, то будет две функции. Тут вроде всё очевидно и вопросов вызывать не должно. Что касается того, стоит ли изменять прототип. Если это изменение упростит половину кода, то, на мой взгляд, это оправдано. Если же это делается ради одной функции, то, скорее всего, нет. Для любых глобальных изменений стоит проявлять разумность и осторожность.

Ответ 2



Object.keys(obj)[index] например, где obj - объект в котором мы ищем. Не вполне ослоустойчиво, будет работать в IE 9+. Можно использовать _.keys(obj)[index] из underscore, это все сократит на пару символов =). Кстати я не уверен, что лексикографический (да и вообще какой-то) порядок ключей нам гарантирован при этом, скорее всего массив ключей надо дополнительно сортировать.

Ответ 3



TL;DR: Порядок ключей в объекте JS не гарантируется. Для сохранения порядка лучше юзать массив. Из личного опыта: Браузеры стараются придерживаться того порядка полей, в котором они были определены. Но на это рассчитывать не стоит. Например, при общении с сервером через WebApi порядок может сбится. Практический пример: в python объекты JSON преобразуется в словарь dict. А в нем уж точно порядок полей не сохраняется и может поменятся произвольно при сериализации обратно в JSON. Объекты JS - это хеш-таблицы, т.е. пары ключ-значение. Порядок пар в такой структуре данных не имеет значения. Они удобны для обращения по ключу со сложностью O(1) (т.е. вне зависимости от числа этих пар). Из спецификации: Порядок ключей в Object.keys такой же, как при перечислении через for...in. В описании же for...in сказано in arbitrary order, что значит "в произвольном порядке". Косвенные признаки: В консоли Chrome и во время отладки свойства идут в алфавитном порядке. А при проходе через for...in - в порядке определения. То, что хром так пренебрежительно относится к порядку ключей объекта, говорит о том, что он не имеет никакого значения. В JS нет никаких явных способов изменить порядок полей. Или хотя бы вставить поле в середину объекта.

Ответ 4



var key = function(obj, n) { return obj[Object.keys(obj)[n]]; } key(key(d, 0), 0); Если вы хотите порядок сохранять, то передалайте на массивы: plane: [{ 432: { columns: [{ 543: { name: 'lolo' }, 984: { name: 'lala' }, ... }, ... ] }, ... }, ... ]

суббота, 4 января 2020 г.

Как оптимизировать запрос

#mysql #запрос #index

Добрый день, есть вот такая таблица:

CREATE TABLE IF NOT EXISTS `ip_city` (
  `ip_from` int(10) unsigned NOT NULL,
  `ip_to` int(10) unsigned NOT NULL,
  `locid` int(10) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8;


Индексы:

ip_from BTREE   ip_from
ip_to   BTREE   ip_to
ip_from_2   BTREE   ip_from, ip_to


И запрос:

SELECT * FROM `ip_city` WHERE (`ip_from` < 2995257412) AND (`ip_to` > 2995257412)


Никак не могу добиться вменяемого результата, никакой индекс не цепляет.
    


Ответы

Ответ 1



Выборки из одной таблицы Возьмем таблицу пользователей с набором личной информации, проиндексированную по адресу электронной почты. Вот пара простых условий, которые могут получить преимущества от индексов: EmailAddress = 'vasya.pupkin@mail.ru' написал равно вместо LIKE так как сам удивился результатам EXPLAIN'а, нужны дополнительные исследования - точно определенное значение всегда имеет возможность использовать индекс, сервер пройдется по дереву и получит точное указание на запись или несколько записей в таблице. Сразу нужно отметить, что, определяя колонку уникальной, автоматически создается индекс по ней. Зачем? Иначе было бы накладно перед каждой вставкой или изменением в таблице проверять все значения поля на соответствие условию уникальности, а так можно быстро проверить существование записи. EmailAddress LIKE 'vacya.pupkin@%' - частичное использование индекса. Повторю, что должна быть определена крайняя левая часть и только она может быть использована для поиска по индексам. Например, для условия EmailAddress LIKE 'vasya.%@mail.ru' тоже будет использован индекс, но в поиске в структуре индекса будет участвовать только vasya., а остальная часть будет проверена последовательным сканированием строк, найденных с помощью индекса. К этому примеру мы вернемся при рассмотрении особенностей составных индексов. Те же условия распространяются на операции с числами: равенство, больше, меньше и другие. Нетрудно догадаться, что некоторые условия можно привести к альтернативным выражениям с использованием элементарных операций, например, BETWEEN, который тоже оптимизируется. (ссылка на источник) В таком случае вы можете попробовать использовать директиву USE INDEX или FORCE INDEX. UPD В качестве оптимизации также можете попробовать в запросе вместо выборки всех полей, "*", перечислить только те поля, которые вам действительно нужны. Это сократит количество выбираемых и пересылаемых данных.

Ответ 2



Оптимизатор начинает использовать индексы только если по его предварительной оценке, количество записей в результате будет не более 30% от общего количества записей в таблице. Иначе, он абсолютно справедливо считает, что быстрее будет тупо перелопатить все записи таблицы не используя индексы. Индекс не будет использован, если использование индекса требует от MySQL прохода более чем по 30% строк в данной таблице (в таких случаях просмотр таблицы, по всей видимости, окажется намного быстрее, так как потребуется выполнить меньше операций поиска). Поэтому ставьте хоть FORCE INDEX или USE INDEX - быстрее не станет.

вторник, 31 декабря 2019 г.

ArrayList как узнать индекс элемента если известно значение?

#java #android #arraylist #index

Можно ли в java узнать индекс элемента в ArrayList, если известно значение? 

При нажатии на пункт списка показывает значения

@Override
public int getItemCount() {
    return mFilteredCheeses.size();
}

public void filter(String query) {
    mFilteredCheeses = new ArrayList<>();
    for (String cheese : mDefaultCheeses) {
        if(cheese.toLowerCase().contains(query.toLowerCase())) {
            mFilteredCheeses.add(cheese);
        }
    }
    notifyDataSetChanged();
}


А есть ли возможность узнать индекс элемента, например со значением Макс?
    


Ответы

Ответ 1



Есть у ArrayList метод indexOf - он как раз ищет подходящий элемент и выводит его индекс. ArrayList test = new ArrayList<>(); test.add("yo"); test.add("yo2"); System.out.println(test.indexOf("yo2")); // Выведет: 1 Если в списке несколько одинаковых значений, то выведет индекс первого попавшегося.

Ответ 2



Смотря что Вы хотите сделать под формулировкой макс. Если это последний индекс нужного элемента то lastIndexOf(value). Можно через цикл, и там через условие то что Вам надо. напишите подробнее если это не подходит. ArrayList test = new ArrayList<>(); test.add("yo"); test.add("yo2"); test.add("yo3"); test.add("yo2"); System.out.println(test.indexOf("yo2")); System.out.println(test.lastIndexOf("yo2"));

среда, 5 июня 2019 г.

Обращение к объекту, как к массиву

Есть ли простой способ обратиться к ключу объекта по его индексу? Может в Underscore есть магические методы?
Вопрос возник на фоне такой задачи. Есть объект:
plane: { 432: { columns: { 543: { name: 'lolo' }, 984: { name: 'lala' }, ... } }, ... }
Где среди n-го количества plane, и n-го количества column нужно выбрать первый plane и первый column внутри него.
Как сделать это проще всего?


Ответ

Хотя ES6 обеспечивает определённый порядок ключей при обходе, гораздо правильнее и удобнее использовать массив, положив тот ключ внутрь объекта, например, в поле id.

Но если уж очень хочется, то можно сделать так (как-нибудь сократив название):
Object.prototype.getByKeyIndex = function (i) { var key = Object.keys(this)[i]; return key && this[key]; }
Тогда на объекте из вопроса будет такое:
plane.getByKeyIndex(0).columns.getByKeyIndex(1).name // "lala"
Вроде, более-менее нормально выглядит.

Ключ сохраняется в переменную и проверяется, чтобы в таком варианте получилось undefined:
({ undefined: 42 }).getByKeyIndex(256)

Я новичок и хочу у Вас спросить - хорошо ли изменять прототип нативных объектов? Что будет если я добавлю метод, а после кто-то другой тоже Ваш ответ увидит и решит добавить свой, но с таким же методом?
В большинстве случаев изменять прототип Object'а не очень хорошо. Но для защиты от прототипных свойств принято фильтровать for-in через hasOwnProperty. Другой вариант - добавлять в прототип не так, как это сделал я, а через скрытое свойство, чтобы оно не перебиралось.
Если двое добавили одинаковое свойство, то одно из них перезапишет другое. По идее, последнее добавленное должно перезаписать предыдущее, но можно пошаманить с readonly, чтобы осталось более раннее. В любом случае, такая ситуация заведомо плохая и лучше в неё не попадать.
Если двое добавят одну и ту же функцию под разными именами, то будет две функции. Тут вроде всё очевидно и вопросов вызывать не должно.
Что касается того, стоит ли изменять прототип. Если это изменение упростит половину кода, то, на мой взгляд, это оправдано. Если же это делается ради одной функции, то, скорее всего, нет. Для любых глобальных изменений стоит проявлять разумность и осторожность.

среда, 10 апреля 2019 г.

ArrayList как узнать индекс элемента если известно значение?

Можно ли в java узнать индекс элемента в ArrayList, если известно значение?
При нажатии на пункт списка показывает значения
@Override public int getItemCount() { return mFilteredCheeses.size(); }
public void filter(String query) { mFilteredCheeses = new ArrayList<>(); for (String cheese : mDefaultCheeses) { if(cheese.toLowerCase().contains(query.toLowerCase())) { mFilteredCheeses.add(cheese); } } notifyDataSetChanged(); }
А есть ли возможность узнать индекс элемента, например со значением Макс?


Ответ

Есть у ArrayList метод indexOf - он как раз ищет подходящий элемент и выводит его индекс.
ArrayList test = new ArrayList<>(); test.add("yo"); test.add("yo2"); System.out.println(test.indexOf("yo2")); // Выведет: 1
Если в списке несколько одинаковых значений, то выведет индекс первого попавшегося.