Changes between Version 13 and Version 14 of Normalization
- Timestamp:
- 09/22/25 22:40:05 (11 hours ago)
Legend:
- Unmodified
- Added
- Removed
- Modified
-
Normalization
v13 v14 14 14 feedback: feedback_submission_type, feedback_created_at, feedback_description 15 15 submission: submission_id, submission_status, submission_created_at, submission_description, 16 blacklisted_user: blacklisted_ start_date, blacklisted_end_date, reason,blacklisted_about_user16 blacklisted_user: blacklisted_id,blacklisted_start_date, blacklisted_end_date, reason,blacklisted_about_user 17 17 tag: tag_name, 18 18 thread: thread_id, thread_created_at, thread_content … … 37 37 4. {{{ submission_id -> submission_status, submission_created_at, submission_description }}} 38 38 39 5. {{{ {blacklisted_about_user,user_id, thread_id, blacklisted_start_date} ->blacklisted_end_date, reason }}}39 5. {{{ blacklisted_id -> blacklisted_about_user,user_id, thread_id, blacklisted_start_date, blacklisted_end_date, reason }}} 40 40 41 41 6. {{{ thread_id -> thread_created_at, thread_content }}} … … 76 76 77 77 === Анализа на функционални зависности 78 За анализата на функционални зависности ќе го користиме методот на LHS/RHS поделба. Според ов ај метод потребно е да ги поделимеатрибутите во 3 групи, односно атрибути што се среќаваат на лева страна од Функционалните зависности(LHS) и според истата логика атрибути на десна страна и атрибути кои се среќаваат на 2те страни.78 За анализата на функционални зависности ќе го користиме методот на LHS/RHS поделба. Според овој метод потребно е да се поделат атрибутите во 3 групи, односно атрибути што се среќаваат на лева страна од Функционалните зависности(LHS) и според истата логика атрибути на десна страна и атрибути кои се среќаваат на 2те страни. 79 79 80 80 > **LHS**: … … 91 91 === Сегашна нормална форма 92 92 93 Имајќи предвид дека guidelines e повеќе вредносен атрибути, доаѓаме до заклучок дека сегашната имплементација на релација не е ни во 1NF форма.93 Имајќи во предвид дека **guidelines** e повеќе вредносен атрибут, доаѓаме до заклучок дека сегашната имплементација на релацијата не е ни во 1NF форма. 94 94 95 95 === Декомпозиција на R во 1NF 96 Со оделување на guidelinesво посебна релација {{{ R1(thread_id, guideline) }}} и {{{ R2(username, thread_id, password...) }}} постигнуваме релациите да се во 1NF.96 Со оделување на **guidelines** во посебна релација {{{ R1(thread_id, guideline) }}} и {{{ R2(username, thread_id, password...) }}} постигнуваме релациите да се во 1NF. 97 97 98 98 Според досега разгледаното за R1(thread_id, guideline) ги имаме следниве ФЗ: … … 101 101 2. {{{ guideline -> guideline }}} 102 102 103 Според функционалните завис имости, единствената комбинација на атрибути која го задоволува условот за супер клуч е {{{ {thread_id, guideline} }}}, бидејќи {{{ {thread_id, guideline}+ = {thread_id, guideline} }}}. Сепак, со цел да оптимизирамеоперациите на базата (особено внесување и пребарување), ќе воведеме нов сурогат клуч **id** како примарен клуч. Заедно со него ги додаваме и следниве ФЗ {{{ id -> thread_id, guideline }}}.104 105 Ова е практично бидејќи природниот клуч {{{ {thread_id, guideline} }}} содржи guideline, која е varchar атрибут со променлива големина. Ако се користеше само природниот клуч, PostgreSQL ќе креираше B-tree индекс врз guideline, кој е поголем по големина и поради тоа побавно ќе се ажурира при **DRU** операции (потребни се повеќе IO страници за индексирање и податоци). Со воведување на сурогат клуч **id** како мал фиксно-димензионален атрибут (на пр. serial или bigserial), индексите се помали и операциите се поефикасни.106 107 Со ова R1 ни се совпаѓа т со релацијата **topic_guidelines**, отсега понатаму ќе ја референцираме како таква.103 Според функционалните зависности, единствената комбинација на атрибути која го задоволува условот за супер клуч е {{{ {thread_id, guideline} }}}, бидејќи {{{ {thread_id, guideline}+ = {thread_id, guideline} }}}. Сепак, со цел да се оптимизираат операциите на базата (особено внесување и пребарување), ќе воведеме нов сурогат клуч **id** како примарен клуч. Заедно со него ги додаваме и следниве ФЗ {{{ id -> thread_id, guideline }}}. 104 105 Ова е практично, бидејќи природниот клуч {{{ {thread_id, guideline} }}} содржи guideline, која е varchar атрибут со променлива големина. Ако се користеше само природниот клуч, PostgreSQL ќе креираше B-tree индекс врз guideline, кој е поголем по големина и поради тоа побавно ќе се ажурира при **DRU** операции (потребни се повеќе IO страници за индексирање и податоци). Со воведување на сурогат клуч **id** како мал фиксно-димензионален атрибут (на пр. serial или bigserial), индексите се помали и операциите се поефикасни. 106 107 Со ова R1 ни се совпаѓа со релацијата **topic_guidelines**, па понатаму ќе ја референцираме како таква. 108 108 109 109 === Декомпозиција R1 до BCNF … … 113 113 3. {{{ id -> thread_id, guideline }}} 114 114 115 Според тоа што само **id** ги определува сите атрибути({{{ id+ -> id,thread_id,guideline}}}) следува дека единствен суперклуч е **id**.116 117 Клуч за оваа релациja би бил **id**, бидејќи неговиот затварач е {{{ id+ = {thread_id, guideline} }}} и е најмал затварач кој ја определува целата релација.115 Според тоа што само **id** ги определува сите атрибути({{{ id+ -> id,thread_id,guideline}}}) следува дека единствен кандидат клуч е **id**. 116 117 Примарен клуч за оваа релациja би бил **id**, бидејќи неговиот затварач е {{{ id+ = {thread_id, guideline} }}} и е најмал затварач кој ја определува целата релација. 118 118 119 119 Според 2NF релацијата не смеe да содржи парцијални зависности. Ова веќе е задоволено од ФЗ за R1. … … 124 124 125 125 Според ова релацијата е веќе во 3NF. 126 Според BCNF секоја релација потребно е да го задоволува следно во својство:126 Според BCNF секоја релација потребно е да го задоволува следното својство: 127 127 "За секое нетривијално (X->A) важи дека X е суперклуч на R". 128 128 Според тоа што **id** e клуч на R1, следува дека релацијата е во BCNF. 129 129 130 130 === Декомпозиција R во 2NF 131 Доколку би ги избрале само атрибутите на левата страна, во таков случај не би можеле да пристапиме до сите ФЗ во кои е вклучен thread_id. Заради тоа ке го избериме thread_id. Со него имаме:131 Доколку би ги избрале само атрибутите на левата страна, во таков случај не би можеле да пристапиме до сите ФЗ во кои е вклучен thread_id. Заради тоа ќе го избериме thread_id. Со него имаме: 132 132 {{{ 133 133 { … … 142 142 channel_UUID, 143 143 thread_id, 144 blacklisted_about_user,145 144 msg_send_at 146 145 } = { … … 187 186 {{{ R8(thread_id,user_id,asc_started_at, asc_ended_at) }}} 188 187 189 {{{ R9(perm_name) }}} 190 {{{ R10(tag_name) }}} 188 {{{ R9(perm_name,tag_name) }}} 191 189 192 190 === Нормализација на R1 до 3NF 193 Најпрвин да заприметимедека оваа релација е устaри релацијата **users**.191 Може да се запримети дека оваа релација е устaри релацијата **users**. 194 192 За оваа релација важат следниве ФЗс: 195 193 1. {{{user_id -> username, description, password, registered_at, email, sex,is_active,name}}} … … 204 202 205 203 === Нормализација на R2 до 3NF 206 Да заприметиме дека единствени ФЗс за оваа релација се:204 Единствени ФЗс за оваа релација се: 207 205 1. {{{ submission_id -> feedback_submission_type, feedback_created_at, feedback_description }}} 208 206 … … 217 215 === Нормализација на R2 до BCNF 218 216 219 Од претходниот чекор, согледаме дека имаме само една ФЗ, што значи дека таа ФЗ мора да содржи суперклуч за релациjaта. Според претходно дискусираното согледувамедека **R2** e веќе во BCNF.217 Од претходниот чекор, може да согледаме дека имаме само една ФЗ, што значи дека таа ФЗ мора да содржи суперклуч за релациjaта. Според претходно спомнатото може да се заклучи дека **R2** e веќе во BCNF. 220 218 221 219 === Подобрување на нормализација на R2 222 220 223 Oд д емонот на апликацијата согледува дека не секој submission мора да има feedback, тоа значи дека доста инстанци ќе имат null вредности за колоните feedback_submission_type, feedback_created_at, feedback_description. Со цел одбегнување на записи со достаnull вредности ќе изведиме 2 нови релации.221 Oд доменот на апликацијата се согледува дека не секој submission мора да има feedback, тоа значи дека доста инстанци ќе имат null вредности за колоните feedback_submission_type, feedback_created_at, feedback_description. Со цел одбегнување на записи со голем број null вредности ќе изведиме 2 нови релации. 224 222 225 223 1. {{{ R21(submission_id,submission_status, submission_created_at, submission_description) }}} 226 224 2. {{{ R22(submission_id,feedback_submission_type, feedback_created_at, feedback_description) }}} 227 225 228 На ов ај начин доколку некој submission нема feedback тогаш нема да има запис во **R22** и нема да има null вредности во записите. За разлика од претходното решение доста каде што feedback колоните би биле полни со null вредности.226 На овој начин доколку некој submission нема feedback тогаш нема да има запис во **R22** и нема да има null вредности во записите. За разлика од претходното решение доста каде што feedback колоните би биле полни со null вредности. 229 227 230 228 Притоа да согледаме дека **R21** e релациjaта **submission** и **R22** е **feedback**. … … 244 242 245 243 246 247 244 === Нормализација на R4 до 3NF 248 ФЗс прис турни во оваа релација се:245 ФЗс присутни во оваа релација се: 249 246 250 247 1. {{{ thread_id -> thread_created_at, thread_content, topic_title, parent_id, repo_url, project_title }}} … … 257 254 {{{ R43(thread_id, project_title, topic_title, parent_id) }}} 258 255 259 Може да согледаме дека **thread_created_at** и **thread_content** се повторуваат во **R41** и **R42**, па според тоа може да ги изведимево една заедничка релација, односно релацијата **R43**.260 Според тоа ги добиваме следниве релации:256 **thread_created_at** и **thread_content** се повторуваат во **R41** и **R42**, па според тоа може да се изведат во една заедничка релација, односно релацијата **R43**. 257 Според тоа се добиваат следните релации: 261 258 262 259 {{{ R41(project_title, repo_url) }}} … … 264 261 {{{ R43(thread_id, project_title, topic_title, parent_id, thread_created_at, thread_content) }}} 265 262 266 Од тоа што **thread** може да е или проект или топик, но не и двете, тоа повлекува дека:263 Од тоа што **thread** може да е или проект или topic, но не и двете. Tоа повлекува дека: 267 264 268 265 - **thread** е проект -> **topic_title**, **parent_id** се null вредности. 269 - **thread** е топик-> **project_title** е null вредност.266 - **thread** е topic -> **project_title** е null вредност. 270 267 271 268 Со цел да избегнеме null вредности и да обезбедиме **lossless join** ќе го направиме следното: … … 274 271 - **R42** ќе додадеме **thread_id** (за постигнување на **lossless join**), додека од **R43** ќе остраниме **topic_title**, **parent_id**. 275 272 276 Со тоа ги добиваме следниве релации:273 Со тоа се добиваат следните релации: 277 274 278 275 {{{ R41(project_title, repo_url, thread_id) }}} … … 285 282 2. {{{ project_title -> repo_url, thread_id }}} 286 283 287 Лесно се согледува дека {{{ thread_id }}} и {{{project_title}}} се кандидат клучеви, па според тоа бидејќи немаме ниту еден атрибут на левата старна во ФЗти, ко ине е кандидат клуч, релацијата е во BCNF.284 Лесно се согледува дека {{{ thread_id }}} и {{{project_title}}} се кандидат клучеви, па според тоа бидејќи немаме ниту еден атрибут на левата старна во ФЗти, кој не е кандидат клуч, релацијата е во BCNF. 288 285 289 286 Притоа да согледаме дека **R41** е релацијата **project_thread**. … … 295 292 3. {{{ parent_id -> topic_title, thread_id }}} 296 293 297 Бијдеќи {{{ parent_id }}} и {{{thread_id}}} се кандидат клучеви( {{{ {parent_id, topic_title} }}} е супер клуч) не постои ФЗ ,во која левата страна не е супер клуч. Тоа значи дека **R42** e во BCNF.294 Бијдеќи {{{ parent_id }}} и {{{thread_id}}} се кандидат клучеви( {{{ {parent_id, topic_title} }}} е супер клуч) не постои ФЗ во која левата страна не е супер клуч. Тоа значи дека **R42** e во BCNF. 298 295 299 296 Притоа да согледаме дека **R42** е релацијата **topic_thread**. … … 312 309 {{{channel_UUID -> channel_name,channel_description}}} 313 310 314 R6 е веќе во BCNF, заради тоа што единствената ФЗ го вклучува суперклучот и нема транзитивни завис имости.311 R6 е веќе во BCNF, заради тоа што единствената ФЗ го вклучува суперклучот и нема транзитивни зависности. 315 312 316 313 Притоа да согледаме дека **R5** е релацијата **channel**. … … 321 318 {{{pr_id -> pr_name, pr_override_type}}} 322 319 323 **R6** е веќе во BCNF, заради тоа што единствената ФЗ го вклучува суперклучот и нема транзитивни завис имости.324 325 Да заприметиме дека **R6** е уствари**project_role**.320 **R6** е веќе во BCNF, заради тоа што единствената ФЗ го вклучува суперклучот и нема транзитивни зависности. 321 322 Може да се согледа дека **R6** е всушност **project_role**. 326 323 327 324 === Нормализација на R7 до BCNF … … 330 327 {{{ {thread_id, msg_send_at, user_id} -> msg_content}}} 331 328 332 **R7** е веќе во BCNF, заради тоа што единствената ФЗ го вклучува суперклучот и нема транзитивни завис имости.329 **R7** е веќе во BCNF, заради тоа што единствената ФЗ го вклучува суперклучот и нема транзитивни зависности. 333 330 334 331 Притоа да согледаме дека **R7* е релацијата **messages**. … … 343 340 Пртиоа да согледаме дека **R8** е релацијата ** developer_associated_with_project**. 344 341 345 === Нормализација на R9 до BCNF346 Најпрвин да заприметиме дека R9 е всушност релацијата **permissions**.347 348 Бидејќи немаме транзитивни релации и бидејќи {{{ perm_name+ = {perm_name} }}} е супер клуч на релацијата, добиваме дека **R9** е во BCNF.349 350 === Нормализација на R10351 Најпрвин да заприметиме декa R10 е уствари релацијата **tag**. Исто како и кај **R9**, лесно се согледува дека и оваа релација е во BCNF.352