Жалпы рейтингті есептеудің үздік тәжірибелері

Менде LAMP негізіндегі бизнес қосымшасы бар. SugarCRM дәлірек болуы керек. Қазіргі кезде 120+ белсенді пайдаланушы бар. Күн сайын әрбір пайдаланушы «жеке рейтинг» деп аталатын күрделі есепте пайдаланылатын кейбір жазбаларды жасайды.

Бір «жеке рейтинг» мәнін есептеу үшін шамамен 6 секунд қажет. Ал бұрын үлкен мәселе болмады: әр пайдаланушы «жеке рейтинг» есептеулерін бастау үшін берілген сілтемеге шығады, 6-7 секунд күтеді және көрсетілген мәнді ала алады.

Бірақ қазір жалпы рейтингті есептеуді енгізуім керек. Бұл «жеке рейтингіге» қосымша пайдаланушыға есептеп, көрсетуім керек дегенді білдіреді:

  • Қолданбаның барлық пайдаланушылары арасында ең аз жеке рейтинг

  • Қолданбаның барлық пайдаланушылары арасында ең жоғары жеке рейтинг

  • барлық жеке рейтингтер ауқымында қолданыстағы пайдаланушы позициясы.

Айтуынша, қолданыстағы қолданушы 220 ұпайға тең, жекелеген рейтингі 80, ең жоғарғы көрсеткіш - 235 және барлық пайдаланушылар арасында 23-ші орында.

Негізгі мәселелер қалай шешіледі (imho)?

  1. Егер бір есептеу 6 секундқа созылса, бұл жалпы есептеулер 10 минуттан артық уақытты алады. Менің ойымша, осы кезеңде өтінімді дерлік қол жетімсіз етудің қажеті жоқ деп ойлаймын. Ал егер тұтынушылар саны жақын арада 2-3 есе өсетін болса, не болады?

  2. Бұл есептеулер түнгі жұмыс ретінде жасалуы мүмкін, бірақ барлық пайдаланушылар түрлі уақыт белдеулерінде. Ресейде төтенше уақыт белдеулерінің арасындағы айырмашылық 9 сағатты құрайды. Сондықтан Ресейдің батыс бөлігінде адамдар әлі күнге дейін «бүгін» жұмыс істейді. Шығыс бөлігіндегі адамдар «ертең» жұмыс істей бастады. Сонымен, бұл жағдайда түнгі уақытта жұмыс істеудің ең жақсы уақыты қандай?

Мұндай рейтингтік жүйені құруға арналған үздік тәсілдер | тәсілдер | алгоритмдер бар ма?

0
Менің ойымша басты мәселе: бір рейтингті есептеу үшін неге 6-7 секунд қажет?
қосылды автор alzaimar, көзі
Бұл негізінен SQL сұрауды орындауға арналған уақыт.
қосылды автор erop, көзі
Бұл негізінен SQL сұрауды орындауға арналған уақыт.
қосылды автор erop, көзі
Бұл негізінен SQL сұрауды орындауға арналған уақыт.
қосылды автор erop, көзі

6 жауаптар

Тек берілген ақпарат ескеріле отырып, мен көретін жалғыз нұсқалар:

  1. The obvious one - reduce the time taken for a rating calculation (6 seconds to calculate 1 user's rating seems like a lot)

  2. If possible, have intermediate values which you only recalculate some of, as required (for example, have 10 values that make up the rating, all based on different data, when some of the data changes, flag the appropriate values for recalcuation). Either do this recalculation:

    • During your daily recalculation or
    • When the update happens
  3. Partial batch calculation - only recalculate x of the users' ratings at chosen intervals (where x is some chosen value) - has the disadvantage that, at all times, some of the ratings can be out of date

  4. Calculate if not busy - either continuously recalculate ratings or only do so at a chosen interval, but instead of locking the system, have it run as a background process, only doing work if the system is idle

0
қосылды

Тек берілген ақпарат ескеріле отырып, мен көретін жалғыз нұсқалар:

  1. The obvious one - reduce the time taken for a rating calculation (6 seconds to calculate 1 user's rating seems like a lot)

  2. If possible, have intermediate values which you only recalculate some of, as required (for example, have 10 values that make up the rating, all based on different data, when some of the data changes, flag the appropriate values for recalcuation). Either do this recalculation:

    • During your daily recalculation or
    • When the update happens
  3. Partial batch calculation - only recalculate x of the users' ratings at chosen intervals (where x is some chosen value) - has the disadvantage that, at all times, some of the ratings can be out of date

  4. Calculate if not busy - either continuously recalculate ratings or only do so at a chosen interval, but instead of locking the system, have it run as a background process, only doing work if the system is idle

0
қосылды

Тек берілген ақпарат ескеріле отырып, мен көретін жалғыз нұсқалар:

  1. The obvious one - reduce the time taken for a rating calculation (6 seconds to calculate 1 user's rating seems like a lot)

  2. If possible, have intermediate values which you only recalculate some of, as required (for example, have 10 values that make up the rating, all based on different data, when some of the data changes, flag the appropriate values for recalcuation). Either do this recalculation:

    • During your daily recalculation or
    • When the update happens
  3. Partial batch calculation - only recalculate x of the users' ratings at chosen intervals (where x is some chosen value) - has the disadvantage that, at all times, some of the ratings can be out of date

  4. Calculate if not busy - either continuously recalculate ratings or only do so at a chosen interval, but instead of locking the system, have it run as a background process, only doing work if the system is idle

0
қосылды

(Өкінішке орай, «ұзақ» түсініктемелерді жіберіп, жауап беруді жөн көрді)

@Dukeling

Жоғарыда аталған есептеу үшін дерлік барлық уақытты талап ететін SQL сұрауы PHP кодында орындалуы қажет бизнес логикасының репликациясы ғана. Логика есептеу уақытын қысқартуға деген үмітпен SQL-ге ауыстырылды. OK, мен SQL сұрауын оңтайландыруға және PHP кода логиканы орындау арқылы ойнауға тырысамын.

Осы оңтайландырылған қолданба тек жеке секундына 1 секунд есептейді. Тамаша! Дегенмен, бұл жағдайда жүйеге кірген бірінші пайдаланушы 120 секунд күтеді (120+ пайдаланушылар * 1 сек = 120 сек.) Жалпы рейтингті есептеу үшін және оның орнына ие болады.

Мен мынадай тәсілдерді енгізуді ойлаймын:

  1. Let’s have 2 “overall ratings” – “today” and “yesterday”.

  2. For displaying purposes we’ll use “yesterday” overall rating represented as huge already sorted PHP array.

  3. When user hits calculation link he started “today” calculation but application displays him “yesterday” value. Thus we have quickly accessible “yesterday” rating and each user randomly launches rating calculation that will be displayed for them tomorrow.

  4. User list are partitioned by timezones. Each hour a cron job started to check if there’re any users in selected timezone that don’t have “today” individual rating calculated (e.g. user didn’t log into application). If so, application starts calculation of individual rating and puts its value in “today” (still invisible) ovarall rating array. Thus we have a cron job that runs nightly for each timezone-specific user group and fills the probable gaps in case users didn’t log into system.

  5. After all users in all timezones had been worked out, application
    1. sorts “today” array,
    2. drops “yesterday” one,
    3. rename “today” in “yesterday” and
    4. initialize new “today”.

Сіз бұл туралы не ойлайсыз? Бұл жеткілікті ме?

0
қосылды

(Өкінішке орай, «ұзақ» түсініктемелерді жіберіп, жауап беруді жөн көрді)

@Dukeling

Жоғарыда аталған есептеу үшін дерлік барлық уақытты талап ететін SQL сұрауы PHP кодында орындалуы қажет бизнес логикасының репликациясы ғана. Логика есептеу уақытын қысқартуға деген үмітпен SQL-ге ауыстырылды. OK, мен SQL сұрауын оңтайландыруға және PHP кода логиканы орындау арқылы ойнауға тырысамын.

Осы оңтайландырылған қолданба тек жеке секундына 1 секунд есептейді. Тамаша! Дегенмен, бұл жағдайда жүйеге кірген бірінші пайдаланушы 120 секунд күтеді (120+ пайдаланушылар * 1 сек = 120 сек.) Жалпы рейтингті есептеу үшін және оның орнына ие болады.

Мен мынадай тәсілдерді енгізуді ойлаймын:

  1. Let’s have 2 “overall ratings” – “today” and “yesterday”.

  2. For displaying purposes we’ll use “yesterday” overall rating represented as huge already sorted PHP array.

  3. When user hits calculation link he started “today” calculation but application displays him “yesterday” value. Thus we have quickly accessible “yesterday” rating and each user randomly launches rating calculation that will be displayed for them tomorrow.

  4. User list are partitioned by timezones. Each hour a cron job started to check if there’re any users in selected timezone that don’t have “today” individual rating calculated (e.g. user didn’t log into application). If so, application starts calculation of individual rating and puts its value in “today” (still invisible) ovarall rating array. Thus we have a cron job that runs nightly for each timezone-specific user group and fills the probable gaps in case users didn’t log into system.

  5. After all users in all timezones had been worked out, application
    1. sorts “today” array,
    2. drops “yesterday” one,
    3. rename “today” in “yesterday” and
    4. initialize new “today”.

Сіз бұл туралы не ойлайсыз? Бұл жеткілікті ме?

0
қосылды

(Өкінішке орай, «ұзақ» түсініктемелерді жіберіп, жауап беруді жөн көрді)

@Dukeling

Жоғарыда аталған есептеу үшін дерлік барлық уақытты талап ететін SQL сұрауы PHP кодында орындалуы қажет бизнес логикасының репликациясы ғана. Логика есептеу уақытын қысқартуға деген үмітпен SQL-ге ауыстырылды. OK, мен SQL сұрауын оңтайландыруға және PHP кода логиканы орындау арқылы ойнауға тырысамын.

Осы оңтайландырылған қолданба тек жеке секундына 1 секунд есептейді. Тамаша! Дегенмен, бұл жағдайда жүйеге кірген бірінші пайдаланушы 120 секунд күтеді (120+ пайдаланушылар * 1 сек = 120 сек.) Жалпы рейтингті есептеу үшін және оның орнына ие болады.

Мен мынадай тәсілдерді енгізуді ойлаймын:

  1. Let’s have 2 “overall ratings” – “today” and “yesterday”.

  2. For displaying purposes we’ll use “yesterday” overall rating represented as huge already sorted PHP array.

  3. When user hits calculation link he started “today” calculation but application displays him “yesterday” value. Thus we have quickly accessible “yesterday” rating and each user randomly launches rating calculation that will be displayed for them tomorrow.

  4. User list are partitioned by timezones. Each hour a cron job started to check if there’re any users in selected timezone that don’t have “today” individual rating calculated (e.g. user didn’t log into application). If so, application starts calculation of individual rating and puts its value in “today” (still invisible) ovarall rating array. Thus we have a cron job that runs nightly for each timezone-specific user group and fills the probable gaps in case users didn’t log into system.

  5. After all users in all timezones had been worked out, application
    1. sorts “today” array,
    2. drops “yesterday” one,
    3. rename “today” in “yesterday” and
    4. initialize new “today”.

Сіз бұл туралы не ойлайсыз? Бұл жеткілікті ме?

0
қосылды