Javascript.RU

Создать новую тему Ответ
 
Опции темы Искать в теме
  #21 (permalink)  
Старый 21.08.2011, 08:21
Профессор
Отправить личное сообщение для popov654 Посмотреть профиль Найти все сообщения от popov654
 
Регистрация: 22.09.2010
Сообщений: 217

Не, но на будущее я обязательно учту)
Кстати, может быть Вы что-нибудь и по другому моему проекту посоветуете (общая суть там похожа)?
Это школьный классный журнал, там редактируются оценки учителями по разным предметам. Он ещё сильно недоработан: нет разграничений прав доступа для разных учителей, нет диаграмм статистики красивых... Но он уже вполне себе функционирует (текущая версия 3.2, сборка 28/07/2009).
Вопрос: как ускорить сохранение и загрузку данных (идеи есть, но хотелось бы услышать предложения от кого-то ещё) и заодно снять лимит в 50 колонок (оценок)? Сейчас схема ужасно тупая и неграмотная: ВСЕ данные берутся из базы, выводятся в гигантскую форму... потом форма редактируется, юзер (педагог) нажимает кнопку... и вся эта куча данных уходит на сервер. Старая таблица предмета очищается и всё вносится по новой. Я конечно понимаю, что это не PHP форум... и всё же, здесь ведь работа на стыке)

Последний раз редактировалось popov654, 22.08.2011 в 10:39.
Ответить с цитированием
  #22 (permalink)  
Старый 21.08.2011, 08:38
Профессор
Отправить личное сообщение для popov654 Посмотреть профиль Найти все сообщения от popov654
 
Регистрация: 22.09.2010
Сообщений: 217

Есть мысль во-первых грузить не всё... И сохранять видимо тоже не всё, а только то, что поменялось.
Далее, для этого видимо стоит как-то привязать id записей в базе к текстовым полям. Не, ну то есть понятно, как привязать, но сейчас там немножко другая схема... при нажатии на кнопку "вставить столбец" пустой столбец вставляется в произвольное место таблицы, но (!) посредством PHP при перезагрузке. То есть скрипт читает данные из базы, генерирует разметку HTML и в нужном месте вставляет пустые ячейки в каждой строке. Но все id ячеек-инпутов идут последовательно и с id записей в базе никак не связаны (если удалить столбец из середины, то скрипт просто его в разметку формы не выведет, и при сохранении эти данные на сервер не пойдут, так как в форме ввода их уже нет). И id при перезаписи базы уже будут другие (так как id определяются тем инпутом, куда попали данные при выводе).

Проблема там ещё и в том, что id местами используется скриптом для сортировки данных вместо других параметров. Кроме того, id инпутов задают ещё и порядок сбора данных из глобального массива $_POST[] при записи в базу. Если я привяжу как сказал, то при вставке столбца в таблицу нумерация вся при таком подходе нарушится, то есть запись должна производиться слева направо, а будет производиться (скрипт идёт по возрастанию id инпутов) вообще хаотично (мы ведь вставку колонок делали), то есть порядок записи непредсказуем. Значит надо и запись перестраивать заодно...

Вот и думаю: может, когда фокус уходит с поля с оценкой, сразу и данные отправлять в базу (в случае успешной валидации разумеется, валидация уже есть)? Тогда и скрипт записи проще станет. Правда, с сортировкой при выводе надо будет поработать, чтобы она id нигде не использовала
Ответить с цитированием
  #23 (permalink)  
Старый 21.08.2011, 11:29
Профессор
Отправить личное сообщение для popov654 Посмотреть профиль Найти все сообщения от popov654
 
Регистрация: 22.09.2010
Сообщений: 217

Кстати, я сделал ещё одну группировку, на этот раз полную. Долго думал на чём делать - на PHP или на JavaScript, в итоге выбрал последнее. На PHP конечно вышло бы проще и быстрее в плане отладки, но... там потом было бы заморочно интегрировать это дело, разбираться со строкой запроса в трекере, продумывать как осуществить отключение левого флажка группировки смежных сессий... Иначе при первом нажатии ничего не произойдёт, а при втором функция попытается заведомо сгруппированную разметку разгруппировать, и выйдет... ну ничего страшного не выйдет, но общей хронологии не будет после такого действия. В отличие от штатного режима группировки подряд идущих сессий с одного IP, оно совершенно обратимо, и после разгруппировки общая хронология сохраняется... Ведь она в сущности и не нарушалась (в отличие от того, что я сделал сейчас).

Выкрутился так: обработка через JavaScript по аналогии с первой функцией, и оба флажка блокируются до загрузки нового блока данных (по нажатию на третий флажок), однако поскольку тут вычислительная сложность куда больше, то браузер на небольшое время всё-таки виснет. Mozilla Firefox выполняет операцию примерно за 3/4 секунды с небольшим, IE - за 2 секунды. Для сравнения - простая группировка в Firefox происходит почти мгновенно (около 1/4 секунды), в IE - за 1 секунду с небольшим (замерял только что). Но Опера всех превзошла, я просто в ауте. Она ОБЕ группировки моментально делает, за доли секунды. КАК им это удалось?
В принципе для анализатора логов лёгкие тормоза не критичны... Однако мне всё-таки жутко интересно, как ВКонтакте делают такой быстрый код (да и не только они, взять хоть формочку редактирования сообщения, в которую я сейчас пишу, она вообще вылетает мгновенно практически по нажатию на кнопку)

Последний раз редактировалось popov654, 21.08.2011 в 11:45.
Ответить с цитированием
  #24 (permalink)  
Старый 21.08.2011, 11:47
Профессор
Отправить личное сообщение для popov654 Посмотреть профиль Найти все сообщения от popov654
 
Регистрация: 22.09.2010
Сообщений: 217

Итоговый код третьей функции:

function groupByIP() {
    var tables = document.getElementsByTagName('table')
    for (var i = 0; i < tables.length; i++) {   //для каждой таблицы в документе
        var map = new Array()           //здесь будем хранить объекты (небольшие ассоциативные массивы)
                                                 //с информацией о группах
        var rows = tables[i].rows
        for (var j = 1; j < rows.length; j++) {   //для каждой строки в таблице
            var found = false      //этот флаг сигнализирует о том, что группа уже существует, т.е. её объект найден
            for (var k = 0; k < map.length; k++) {    //обходим массив map
                if (map[k]['ip'] == rows[j].cells[0].innerHTML) {   //группа найдена!
                    found = true
                    var index = map[k]['from'] + map[k]['entries']        //вычисляем позицию для вставки новой строки
                                                                                        //(вставляем снизу)
                    if (index == j) {      //если первая строка группы прямо над нами, удалять текущую строку незачем
                        rows[j].deleteCell(0)         //вместо этого удаляем в ней первую и последнюю ячейки
                        rows[j].deleteCell(-1)
                    } else {
                        tables[i].insertRow(index)      //вставляем новую строчку в таблицу
                        if (index <= j) j++;           //если вставка произошла выше, корректируем текущий индекс j (!)
                        for (var m = 3; m >= 1; m--) {     //добавляем в новую строку ячейки и копируем содержимое
                            rows[index].insertCell(0)
                            rows[index].cells[0].innerHTML = rows[j].cells[m].innerHTML
                        }
                        rows[index].cells[0].align = 'center'     //копируем атрибуты
                        tables[i].deleteRow(j)    //удаляем старую строку
                        if (index <= j) j--;      //и корректируем индекс в обратную сторону (!!)
                    }
                    rows[map[k]['from']].cells[0].rowSpan += 1      //расширяем первую и последнюю ячейки
                    rows[map[k]['from']].cells[4].rowSpan += 1      //ещё на одну строчку вниз
                    rows[map[k]['from']].cells[0].style.verticalAlign = 'top'      //Ставим выравнивание так, чтобы текст в
                    rows[map[k]['from']].cells[4].style.verticalAlign = 'top'      //огромных ячейках выводился сверху, а не
                                                                                          //посередине
                    map[k]['entries']++  //увеличиваем размер группы на единицу
                    for (var l = 0; l < map.length; l++) {   //(важно!) проходим по всему массиву объектов и у тех групп,
                                                             //которые расположены ниже по таблице, корректируем
                                                             //начальные индексы
                        if (map[l]['from'] > map[k]['from']) {
                            map[l]['from']++
                        }
                    }
                    break;  //дальше по массиву можно не идти
                }
            }
            if (!found) {     //если же группа не найдена, создаём для неё новый объект...
                var entry = {
                    from: j,
                    ip: rows[j].cells[0].innerHTML,
                    entries: 1
                }
                map.push(entry)   //и помещаем его в массив map
            }
        }
    }
}

Последний раз редактировалось popov654, 21.08.2011 в 12:08. Причина: Добавил комментарии
Ответить с цитированием
  #25 (permalink)  
Старый 21.08.2011, 11:48
Отправить личное сообщение для Octane Посмотреть профиль Найти все сообщения от Octane  
Регистрация: 10.07.2008
Сообщений: 3,873

Сорри, не осилил многабукф
Ответить с цитированием
  #26 (permalink)  
Старый 21.08.2011, 13:02
что-то знаю
Отправить личное сообщение для devote Посмотреть профиль Найти все сообщения от devote
 
Регистрация: 24.05.2009
Сообщений: 5,176

дауж... аж глаза разбежались... Сложно воспринять такое количество букв.. Не надо описывать все свои действия и то как оно и почему оно у тебя так сработало. Просто опиши проблему и все.

P.S. Читаю форум и вижу:
Цитата:
Я запускаю браузер, вбиваю адрес перехожу на сайт, там кликаю ссылку, после чего кликаю другую потом ввожу пару параметров и у меня ничего не происходит.
...................................
вот тут он приводит в пример многа кода, букв и т.д.
...................................
Итог: человек описал проблему, как написал книгу, рассказывая совершенно ненужный материал и выдал куча кода, но не описал простого, или не описал по простому:
Цитата:
например есть функция "Alert" и она не срабатывает, вот фрагмент кода с участком данной команды.
.........тут код
Все, вот и простое объяснение.
Ответить с цитированием
  #27 (permalink)  
Старый 21.08.2011, 20:36
Профессор
Отправить личное сообщение для popov654 Посмотреть профиль Найти все сообщения от popov654
 
Регистрация: 22.09.2010
Сообщений: 217

Не, я извиняюсь)
Вы не так поняли)
Проблема решена уже давно, я этот код так выложил... для истории. Ну вдруг кого-то заинтересует когда-нибудь. А всё что я пишу начиная с середины второй страницы - оффтоп, не имеющий ничего общего с темой треда. Так что можно тему закрывать

Единственное, что немного волнует - тормознутость этого кода в IE7, причём виноват в этом скорее код чем браузер...
Ответить с цитированием
  #28 (permalink)  
Старый 21.08.2011, 20:38
Профессор
Отправить личное сообщение для popov654 Посмотреть профиль Найти все сообщения от popov654
 
Регистрация: 22.09.2010
Сообщений: 217

Третья функция работает совершенно исправно. Единственное, я думал кто-нибудь предложит какую-нибудь оптимизацию, что-нибудь порациональнее сделать, чтобы быстрее всё это исполнялось. Впрочем, я думаю это вряд ли возможно в этой ситуации
Ответить с цитированием
  #29 (permalink)  
Старый 21.08.2011, 21:06
sinistral
Посмотреть профиль Найти все сообщения от melky
 
Регистрация: 28.03.2011
Сообщений: 5,418

Сообщение от popov654 Посмотреть сообщение
тормознутость этого кода в IE7
один пример :

for (var i = 0; i < tables.length; i++) {

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

т.е. надо так.. примерно

for (var i = 0, tablesLength = tables.length; i < tablesLength; i++) {

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

и еще : попробуйте сжать код, это тоже ускорит его
Ответить с цитированием
Ответ



Опции темы Искать в теме
Искать в теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Картинки-ссылки в меню не работают в IE7 Александр345 Internet Explorer 6 16.06.2011 18:33
Js + Ie7 проблема onuvidelsolnce Internet Explorer 4 28.03.2011 20:21
Взаимодействие фреймов. IE7 Svarog81 Internet Explorer 1 03.03.2011 13:08
слетает верстка в IE6 и IE7 (js используется) rognarek Internet Explorer 3 08.09.2010 19:34
Тормозит подсветка td в IE7 Beck Events/DOM/Window 7 25.04.2010 21:45