លេខ និងប្រព័ន្ធលេខ

មាតិកា

  1. សញ្ញាណតាមទីតាំង៖ អ្វីដែល 345 មានន័យពិតប្រាកដ
  2. Binary៖ Base 2
  3. ការបំប្លែងដោយដៃ
  4. Hexadecimal៖ Base 16
  5. Octal និង Literal ក្នុង JavaScript
  6. toString និង parseInt
  7. ពណ៌ Hex
  8. ហេតុអ្វី 0.1 + 0.2 មិនស្មើ 0.3
  9. ការប្រៀបធៀប Float ដោយសុវត្ថិភាព
  10. រូបមន្ត៖ numbers.js
  11. សាកល្បងដោយខ្លួនឯង

1. សញ្ញាណតាមទីតាំង៖ អ្វីដែល 345 មានន័យពិតប្រាកដ

អ្នកអានលេខ 345 ដោយមិនបាច់គិត។ ប៉ុន្តែខ្ទង់នីមួយៗមានតម្លៃខុសៗគ្នាអាស្រ័យលើ ទីតាំង របស់វា៖

ទីតាំងរយដប់រាយ
ខ្ទង់345
តម្លៃ3 x 1004 x 105 x 1

ដូច្នេះ 345 = 3 x 100 + 4 x 10 + 5 x 1។ សូមមើលតម្លៃទីតាំង៖ 1, 10, 100។ ពួកវាជាស្វ័យគុណនៃ 10៖ 10^0, 10^1, 10^2។ (10^2 មានន័យថា 10 x 10។ ក្នុង JavaScript អ្នកសរសេរវាជា 10 ** 2។)

យើងប្រើខ្ទង់ដប់ គឺ 0 ដល់ 9 ហើយតម្លៃទីតាំងកើនឡើងដង 10។ នោះហៅថា base 10 ឬ ទសភាគ (decimal)។ ហេតុផលតែមួយគត់ដែលយើងប្រើ base 10 គឺមនុស្សមានម្រាមដៃដប់។

គ្មានអ្វីបង្ខំយើងឲ្យប្រើដប់ទេ។ ប្រព័ន្ធលេខ ដែលមាន base b ប្រើខ្ទង់ b ហើយទីតាំងនីមួយៗមានតម្លៃ b ដងនៃទីតាំងនៅខាងស្តាំរបស់វា។ កុំព្យូទ័រចូលចិត្ត base 2 ហើយអ្នកសរសេរកម្មវិធីតែងសរសេរ base 16។

2. Binary៖ Base 2

សៀគ្វីកុំព្យូទ័រគឺបើក ឬបិទ ដូច្នេះប្រព័ន្ធធម្មជាតិមានពីរខ្ទង់៖ 0 និង 1។ នេះគឺ binary។ ខ្ទង់ binary តែមួយហៅថា bit។ តម្លៃទីតាំងគឺជាស្វ័យគុណនៃ 2៖

តម្លៃទីតាំង1286432168421
ស្វ័យគុណ2^72^62^52^42^32^22^12^0

ដើម្បីអានលេខ binary 1101 សូមបូកតម្លៃទីតាំងដែលមាន 1៖

1101 = 1 x 8 + 1 x 4 + 0 x 2 + 1 x 1
     = 8 + 4 + 0 + 1
     = 13

ប្រាំបី bit បង្កើតបាន byte មួយ ហើយ byte មួយអាចផ្ទុក 0 ដល់ 255 (នោះគឺ 2^8 = 256 តម្លៃខុសៗគ្នា)។ ប្រសិនបើអ្នកចង់ទទួលការរំលឹកអំពី bit និង byte សូមមើល Bit និង Byte។

ការរាប់ក្នុង binary មើលទៅដូចនេះ៖

ទសភាគBinary
00
11
210
311
4100
5101
81000
131101
25511111111

ដូចជា 9 ឡើងទៅ 10 ក្នុងទសភាគ ដែរ 1 ឡើងទៅ 10 ក្នុង binary។ លំនាំមានប្រយោជន៍មួយ៖ n bit អាចតំណាងឲ្យ 2^n តម្លៃខុសៗគ្នា។ ប្រាំបី bit ផ្តល់ 256, ដប់ប្រាំមួយ bit ផ្តល់ 65,536 ហើយ 32 bit ផ្តល់ 4,294,967,296។

3. ការបំប្លែងដោយដៃ

Binary ទៅទសភាគ៖ បូកតម្លៃទីតាំង ដូចខាងលើ។

ទសភាគទៅ binary៖ ចែកនឹង 2 ម្តងហើយម្តងទៀត។ សរសេរសំណល់នីមួយៗ។ សំណល់ដែលអានពីចុងក្រោយទៅដំបូង គឺជាខ្ទង់ binary។

បំប្លែង 13៖

ជំហានចែកផលចែកសំណល់
113 / 261
26 / 230
33 / 211
41 / 201

អានសំណល់ពីក្រោមទៅលើ៖ 1101។ វាត្រូវនឹងលទ្ធផលពីមុន។

យើងអាចបំប្លែងតារាងនោះទៅជាកូដ។ វាប្រើ % (សំណល់) និង Math.floor (បង្គត់ចុះ)៖

function manualBinary(n) {
  let out = "";
  while (n > 0) {
    out = (n % 2) + out;     // ដាក់សំណល់នៅ ខាងមុខ
    n = Math.floor(n / 2);   // ចែកជា integer
  }
  return out || "0";
}

console.log(manualBinary(13));  // 1101
console.log(manualBinary(255)); // 11111111
console.log(manualBinary(0));   // 0

ទៅរកផ្លូវផ្ទុយវិញ អ្នកអាចសាងសង់លេខពីខ្ទង់របស់វាពីឆ្វេងទៅស្តាំ។ សម្រាប់ខ្ទង់នីមួយៗ គុណអ្វីដែលអ្នកមានរហូតមកដល់ពេលនេះនឹង base បន្ទាប់មកបូកខ្ទង់៖

function fromDigits(text, base) {
  let total = 0;
  for (const ch of text) {
    total = total * base + parseInt(ch, base);
  }
  return total;
}

console.log(fromDigits("1101", 2)); // 13
console.log(fromDigits("ff", 16));  // 255
console.log(fromDigits("755", 8));  // 493

ពិនិត្យដោយដៃសម្រាប់ 1101៖ ចាប់ផ្តើមពី 0 បន្ទាប់មក 0*2+1 = 1, 1*2+1 = 3, 3*2+0 = 6, 6*2+1 = 13។ ល្បិចនេះហៅថា Horner's method ហើយវាជារបៀបដែល parser ភាគច្រើនអានលេខ។

4. Hexadecimal៖ Base 16

Binary វែង។ លេខ 255 គឺ 11111111 ប្រាំបីខ្ទង់។ Hexadecimal (ហៅខ្លីថា hex) គឺ base 16 ហើយវាជាវិធីបង្រួមដើម្បីសរសេរ binary ព្រោះ ខ្ទង់ hex មួយស្មើនឹងបួន bit យ៉ាងពិតប្រាកដ។

Base 16 ត្រូវការខ្ទង់ដប់ប្រាំមួយ។ យើងមាន 0 ដល់ 9 ដូច្នេះអក្សរបំពេញផ្នែកដែលនៅសល់៖

HexទសភាគBinary
0 ដល់ 90 ដល់ 90000 ដល់ 1001
a101010
b111011
c121100
d131101
e141110
f151111

តម្លៃទីតាំងគឺជាស្វ័យគុណនៃ 16៖ 1, 16, 256, 4096។ ដូច្នេះ ff គឺ 15 x 16 + 15 x 1 = 255 ហើយ 1e គឺ 1 x 16 + 14 = 30។

ដោយសារខ្ទង់ hex នីមួយៗជាបួន bit ការបំប្លែងរវាង binary និង hex មិនត្រូវការនព្វន្តទេ។ ដាក់ bit ជាក្រុមៗបួនពីខាងស្តាំ៖

1101 1111  (binary)
 d    f    (hex)

ដូច្នេះ 11011111 គឺ df ក្នុង hex។ Byte មួយតែងតែជាខ្ទង់ hex ពីរយ៉ាងពិតប្រាកដ គឺ 00 ដល់ ff។ អ្នកនឹងឃើញ hex ក្នុងអាសយដ្ឋានអង្គចងចាំ កូដពណ៌ កូដកំហុស hash និង UUID។

5. Octal និង Literal ក្នុង JavaScript

Octal គឺ base 8៖ ខ្ទង់ 0 ដល់ 7 ហើយខ្ទង់ octal នីមួយៗស្មើនឹងបី bit។ ការប្រើប្រាស់សំខាន់សម័យទំនើបរបស់វាគឺសិទ្ធិឯកសារ Unix ដូចជា 755 ដែលយើងនឹងជួបក្នុងជំពូកបន្ទាប់។

JavaScript អនុញ្ញាតឲ្យអ្នកសរសេរលេខក្នុង base ទាំងនេះដោយផ្ទាល់។ ទាំងនេះហៅថា literal ហើយពួកវាទាំងអស់បង្កើតលេខធម្មតា៖

PrefixBaseឧទាហរណ៍តម្លៃ
គ្មាន10255255
0b20b110113
0o80o1715
0x160xff255
console.log(0b1101); // 13
console.log(0o17);   // 15
console.log(0xff);   // 255
console.log(0xff === 255); // true

លេខមិន "ចងចាំ" ថាអ្នកសរសេរវាដោយរបៀបណាទេ។ 0xff និង 255 គឺជាតម្លៃដូចគ្នា។ Base សំខាន់តែនៅពេលអ្នកសរសេរលេខ ឬបោះពុម្ពវាប៉ុណ្ណោះ។

6. toString និង parseInt

ដើម្បី បោះពុម្ព លេខក្នុង base ផ្សេង សូមប្រើ number.toString(base)។ ដើម្បី អាន អត្ថបទក្នុង base ផ្សេង សូមប្រើ parseInt(text, base)។

console.log((13).toString(2));    // 1101
console.log((255).toString(16));  // ff
console.log((255).toString(8));   // 377
console.log((10).toString(16));   // a

console.log(parseInt("1101", 2)); // 13
console.log(parseInt("ff", 16));  // 255
console.log(parseInt("FF", 16));  // 255 (អក្សរតូចធំមិនសំខាន់)
console.log(parseInt("777", 8));  // 511

តង្កៀបក្នុង (13).toString(2) ត្រូវការ ព្រោះ 13.toString នឹងមើលទៅដូចជាចំណុចទសភាគសម្រាប់ JavaScript។ ត្រូវបញ្ជូន base ទៅ parseInt ជានិច្ច។ ការទុកវាចោលគឺជាប្រភពបុរាណនៃ bug។

សូមដឹងអំពីឥរិយាបថពីរ៖

console.log(parseInt("12px"));  // 12 (ឈប់នៅតួអក្សរខុសដំបូង)
console.log(parseInt("xyz"));   // NaN (មិនមែនលេខ)
console.log((10).toString(16).padStart(2, "0")); // 0a

parseInt មិនអើពើនឹងអត្ថបទដែលនៅសល់ដោយស្ងាត់ៗ ហើយ NaN មានន័យថា "មិនមែនលេខ"។ padStart(2, "0") បន្ថែមលេខសូន្យនៅខាងមុខរហូតដល់អត្ថបទមានពីរតួអក្សរ ដែលយើងត្រូវការសម្រាប់ពណ៌។

7. ពណ៌ Hex

ពណ៌ web ដូចជា #1e90ff គឺជាបីបៃសរសេរជា hex៖ ក្រហម បៃតង និងខៀវ។ ឆានែលពណ៌នីមួយៗគឺ 00 ដល់ ff ដែលជា 0 ដល់ 255។

ផ្នែកHexទសភាគ
ក្រហម1e30
បៃតង90144
ខៀវff255

ដូច្នេះ #1e90ff គឺ rgb(30, 144, 255) ជាពណ៌ខៀវភ្លឺ។ ពណ៌ល្បីៗមួយចំនួន៖

ពណ៌HexRGB
ខ្មៅ#0000000, 0, 0
ស#ffffff255, 255, 255
ក្រហមសុទ្ធ#ff0000255, 0, 0

ចំនួនពណ៌សរុបគឺ 256 x 256 x 256 = 16,777,216 ឬ 2^24។ នោះគឺជាកន្លែងដែលឃ្លា "ពណ៌ 24-bit" កើតឡើង។

ការបំប្លែងគ្រាន់តែជា parseInt(..., 16) សម្រាប់គូតួអក្សរនីមួយៗ និង toString(16) ជាមួយ padding នៅពេលត្រឡប់ទៅវិញ។ ឆានែលដូចជា 5 ត្រូវតែក្លាយជា 05 មិនមែន 5 ទេ បើមិនដូច្នោះកូដនឹងខ្លីពេក។ កំហុសនោះជារឿងធម្មតាខ្លាំងណាស់។

8. ហេតុអ្វី 0.1 + 0.2 មិនស្មើ 0.3

ចំនួនគត់ត្រូវបានរក្សាទុកយ៉ាងត្រឹមត្រូវ។ ប្រភាគពិបាកជាង។

ក្នុងទសភាគ អ្នកមិនអាចសរសេរ 1/3 បានត្រឹមត្រូវទេ៖ វាជា 0.3333... ជារៀងរហូត។ នោះជាបញ្ហារបស់ base។ 1/3 ងាយក្នុង base 3 ហើយមិនអាចទៅរួចក្នុង base 10។ រឿងដូចគ្នាកើតឡើងក្នុង binary ជាមួយប្រភាគដូចជា 0.1។

ទីតាំងបន្ទាប់ពីចំណុច binary មានតម្លៃ 1/2, 1/4, 1/8 ហើយបន្តទៅទៀត។ ប្រភាគខ្លះត្រឹមត្រូវក្នុង binary៖

console.log((0.5).toString(2));  // 0.1
console.log((0.75).toString(2)); // 0.11  (1/2 + 1/4)
console.log((0.25).toString(2)); // 0.01

ប៉ុន្តែ 0.1 (មួយភាគដប់) មិនមែនជាផលបូកនៃបំណែកមួយចំនួនតូចបែបនេះទេ។ ក្នុង binary វាស្ទួនជារៀងរហូត៖

console.log((0.1).toString(2));
// 0.0001100110011001100110011001100110011001100110011001101

JavaScript រក្សាទុកលេខជាតម្លៃ floating-point 64-bit (ស្តង់ដារ IEEE 754 ហៅថា double) ដែលមានកន្លែងសម្រាប់ប្រហែល 53 ខ្ទង់ binary។ ដូច្នេះវាត្រូវ បង្គត់ 0.1 ហើយរក្សាទុកលេខដែលខុសពីមួយភាគដប់បន្តិចបន្តួចណាស់។ អ្នកអាចមើលតម្លៃពិតដែលបានរក្សាទុក៖

console.log((0.1).toFixed(25)); // 0.1000000000000000055511151
console.log((0.2).toFixed(25)); // 0.2000000000000000111022302
console.log((0.3).toFixed(25)); // 0.2999999999999999888977698

លេខនីមួយៗមានកំហុសតូចមួយ។ នៅពេលអ្នកបូក 0.1 + 0.2 កំហុសទាំងនោះផ្សំគ្នា ហើយចម្លើយធ្លាក់នៅលើ 0.3 បន្តិច៖

console.log(0.1 + 0.2);         // 0.30000000000000004
console.log(0.1 + 0.2 === 0.3); // false
console.log(0.1 * 3);           // 0.30000000000000004

នេះ មិនមែនជា bug របស់ JavaScript ទេ។ Python, Java, C និង Swift ផ្តល់ចម្លើយដូចគ្នា ព្រោះពួកវាទាំងអស់ប្រើស្តង់ដារដូចគ្នា។ លេខដែលមានផ្នែកប្រភាគគឺជាការប៉ាន់ស្មាន ហើយនេះជាអ្វីដែលអ្នកគួរចងចាំ៖

  • កុំប្រៀបធៀប float ដោយ === បន្ទាប់ពីការគណនា។
  • កុំរក្សាទុកលុយជា float។ ជំពូក 7 បង្ហាញដំណោះស្រាយ៖ ចំនួនគត់នៃសេន ឬរៀល។
  • ចំនួនគត់រហូតដល់ Number.MAX_SAFE_INTEGER (9007199254740991) គឺត្រឹមត្រូវ។ លេខធំជាងនេះមិនត្រឹមត្រូវទេ។

9. ការប្រៀបធៀប Float ដោយសុវត្ថិភាព

ប្រសិនបើអ្នកមិនអាចសួរថា "តើទាំងនេះស្មើគ្នាយ៉ាងពិតប្រាកដឬទេ?" សូមសួរថា "តើទាំងនេះជិតគ្នាគ្រប់គ្រាន់ឬទេ?"។ ដកពួកវា ហើយពិនិត្យថា តម្លៃដាច់ខាត (ចម្ងាយ មិនគិតសញ្ញា) តូចជាងកម្រិតតូចមួយហៅថា epsilon៖

const a = 0.1 + 0.2;
const b = 0.3;

console.log(Math.abs(a - b)); // 5.551115123125783e-17
console.log(Math.abs(a - b) < 1e-9); // true

លេខ 5.55e-17 គឺជាសញ្ញាណវិទ្យាសាស្ត្រ៖ 0.0000000000000000555។ វាតូចណាស់ ដែលសម្រាប់គោលបំណងជាក់ស្តែងណាមួយ តម្លៃទាំងពីរស្មើគ្នា។

JavaScript មាន Number.EPSILON ភ្ជាប់មកស្រាប់ (ប្រហែល 2.22e-16) ប៉ុន្តែវាគ្រាន់តែជាគម្លាតរវាង 1 និងលេខបន្ទាប់ប៉ុណ្ណោះ។ វាតឹងរ៉ឹងពេកសម្រាប់តម្លៃធំជាង ឬតម្លៃដែលឆ្លងកាត់ការគណនាច្រើន។ សម្រាប់កូដប្រចាំថ្ងៃ សូមជ្រើសរើស epsilon ផ្ទាល់ខ្លួនដែលសមស្របនឹងបញ្ហា៖ 1e-9 សម្រាប់ការប្រើទូទៅ 0.005 បើអ្នកខ្វល់តែពាក់កណ្តាលសេន។

ឧបករណ៍ទីពីរគឺការបង្គត់សម្រាប់បង្ហាញ ដូចក្នុង toFixed៖

console.log((0.1 + 0.2).toFixed(2)); // 0.30

toFixed(2) ត្រឡប់ អត្ថបទ មិនមែនលេខទេ។ ប្រើវាដើម្បីបង្ហាញតម្លៃ មិនមែនដើម្បីប្រៀបធៀបវាទេ។

10. រូបមន្ត៖ numbers.js

បង្កើត src/numbers.js។ វាបំប្លែងរវាង base បំប្លែងពណ៌ hex និងប្រៀបធៀប float៖

export function toBinary(n) {
  return n.toString(2);
}

export function toHex(n) {
  return n.toString(16);
}

export function fromHex(text) {
  return parseInt(text, 16);
}

export function hexToRgb(hex) {
  const clean = hex.replace("#", "");
  return {
    r: fromHex(clean.slice(0, 2)),
    g: fromHex(clean.slice(2, 4)),
    b: fromHex(clean.slice(4, 6)),
  };
}

function twoDigitHex(n) {
  return toHex(n).padStart(2, "0");
}

export function rgbToHex(r, g, b) {
  return "#" + twoDigitHex(r) + twoDigitHex(g) + twoDigitHex(b);
}

export function nearlyEqual(a, b, epsilon = 1e-9) {
  return Math.abs(a - b) < epsilon;
}

កំណត់សម្គាល់ខ្លះ។ hex.replace("#", "") លុប # បើវាមាន ដូច្នេះទាំង "#1e90ff" និង "1e90ff" ដំណើរការ។ slice(0, 2) យកពីរតួអក្សរដំបូង (ក្រហម) slice(2, 4) ពីរបន្ទាប់ (បៃតង) slice(4, 6) ពីរចុងក្រោយ (ខៀវ)។ epsilon = 1e-9 គឺជា default parameter៖ អ្នកហៅអាចទុកវាចោលបាន។

ឥឡូវនេះបន្ថែមវាទៅ src/index.js៖

// Every module we write is re-exported from here.
export const version = "0.1.0";
export * from "./numbers.js";

ជំនួស demo.js ដោយ៖

import {
  version, toBinary, toHex, fromHex,
  hexToRgb, rgbToHex, nearlyEqual,
} from "./src/index.js";

console.log(`mathlab v${version}`);

console.log(toBinary(13));   // 1101
console.log(toBinary(255));  // 11111111
console.log(toHex(255));     // ff
console.log(toHex(3054));    // bee
console.log(fromHex("ff"));  // 255

console.log(hexToRgb("#1e90ff")); // { r: 30, g: 144, b: 255 }
console.log(rgbToHex(30, 144, 255)); // #1e90ff
console.log(rgbToHex(0, 5, 10));     // #00050a

console.log(0.1 + 0.2 === 0.3);          // false
console.log(nearlyEqual(0.1 + 0.2, 0.3)); // true
console.log(nearlyEqual(1, 1.1));         // false
console.log(nearlyEqual(1, 1.0000000001, 1e-6)); // true

រត់វា៖

node demo.js

លទ្ធផលដែលរំពឹងទុក៖

mathlab v0.1.0
1101
11111111
ff
bee
255
{ r: 30, g: 144, b: 255 }
#1e90ff
#00050a
false
true
false
true

(false ដែលបោះពុម្ពភ្លាមបន្ទាប់ពី #00050a គឺជាការប្រៀបធៀប === ធម្មតា ហើយ true បន្ទាប់ពីវាគឺ nearlyEqual។)

សូមកត់សម្គាល់ថា rgbToHex(0, 5, 10) ផ្តល់ #00050a ដោយរក្សាលេខសូន្យនៅខាងមុខ។ សូមលុបការហៅ padStart ហើយមើលថាអ្វីខូច។

11. សាកល្បងដោយខ្លួនឯង

  1. ដោយដៃ។ បំប្លែង 100 ទៅ binary ដោយប្រើតារាងចែកនឹង 2 បន្ទាប់មកពិនិត្យដោយ (100).toString(2)។ បន្ទាប់មកបំប្លែង 10110 ទៅទសភាគដោយបូកតម្លៃទីតាំង។
  2. ផ្លូវកាត់ Hex។ ដោយគ្មានម៉ាស៊ីនគិតលេខ សរសេរ 10101111 ជា hex ដោយដាក់ជាក្រុមៗបួន។ ផ្ទៀងផ្ទាត់ដោយ parseInt("10101111", 2).toString(16)។
  3. សាងសង់ពណ៌។ ប្រើ rgbToHex ដើម្បីបង្កើតកូដ hex សម្រាប់ rgb(255, 165, 0) (ពណ៌ទឹកក្រូច)។ បន្ទាប់មកហៅ hexToRgb លើលទ្ធផល ហើយពិនិត្យថាអ្នកទទួលបានលេខដូចគ្នាត្រឡប់មកវិញ។
  4. ធ្វើឲ្យភ្លឺជាងមុន។ សរសេរ function lighten(hex, amount) ដែលបូក amount ទៅឆានែលនីមួយៗ ប៉ុន្តែមិនដែលលើស 255។ ប្រើ Math.min។ តើ lighten("#f0f0f0", 30) គួរផ្តល់អ្វី?
  5. អ្នកស៊ើបអង្កេត Float។ ទាយ រួចរត់៖ 0.1 * 3, 0.7 + 0.1, 4.35 * 100 និង 0.5 + 0.25។ មួយណាត្រឹមត្រូវ ហើយហេតុអ្វី? (គន្លឹះ៖ មើលថាប្រភាគណាជាផលបូកនៃពាក់កណ្តាល មួយភាគបួន និងមួយភាគប្រាំបី។)
  6. ជម្រើស Epsilon។ ប្រៀបធៀប 1000000.1 + 0.2 នឹង 1000000.3 ដោយប្រើ nearlyEqual ជាមួយ epsilon 1e-9 និង 1e-12។ តើអ្វីផ្លាស់ប្តូរ? ហេតុអ្វីលេខធំជាងប្រហែលជាត្រូវការ epsilon ធំជាង?

ឥឡូវនេះអ្នកអាចអាន និងសរសេរលេខក្នុង base ណាក៏បាន។ បន្ទាប់ ក្នុង Bitwise Operation និង Flag យើងធ្វើការជាមួយ bit នីមួយៗនៃលេខទាំងនោះ ដើម្បីខ្ចប់ការកំណត់បាទ/ចាសជាច្រើនចូលក្នុងតម្លៃតែមួយ ដូចសិទ្ធិ Unix ធ្វើដែរ។

ទិញកាហ្វេជូនខ្ញុំ

ចូលចិត្តមេរៀននេះមែនទេ? សូមពិចារណាទិញកាហ្វេជូនខ្ញុំមួយកែវ ដើម្បីគាំទ្រការបង្កើតមាតិកាឥតគិតថ្លៃបន្ថែមទៀត!