The below example shows calculating cigaratte, pack, cartoon and box. You can add any units to data_array and calculate among units.
const data_array = [
{
unit: "cigaratte",
rate: 20
},
{
unit: "pack", // 20 cigarattes = 1 pack
rate: 12
},
{
unit: "cartoon", // 10 packs = 1 cartoon
rate: 10
},
{
unit: "box", // 10 cartoon = 1 box
rate: 1
},
];
class CUnit {
constructor(data_array, options) {
this.data_array = data_array;
this.in_decimal = options?.in_decimal;
this.decimal_count = options?.decimal_count ? options?.decimal_count : 2
}
countDecimal(number){
const numberString = number.toString();
if (numberString.includes('.')) {
return parseInt(Math.ceil(number));
} else {
return number;
}
}
findIndexNumbersBetween() {
let start = this.fromIndex;
let end = this.toIndex;
if(start > end){
let prevEnd = end;
end = start;
start = prevEnd;
}
const betweenIndexes = [];
for (let i = start + 1; i < end; i++) {
betweenIndexes.push(i);
}
return betweenIndexes;
}
multiplyOtherIndexes(otherIndexes){
otherIndexes.push(this.toIndex) // add to Index;
let otherIndexesMin = otherIndexes.sort((a, b) => a - b);
let indexRates = otherIndexesMin.map(e=>this.data_array[e].rate).reduce((a,b)=> a * b);
return this.amount * indexRates;
}
divideOtherIndexes(otherIndexes){
otherIndexes.push(this.fromIndex) // add to Index;
let otherIndexesMin = otherIndexes.sort((a, b) => a - b);
return otherIndexesMin.map((e,i)=>{
// if fromIndex
if(i === 0){
return this.amount / this.data_array[e].rate;
}
return this.data_array[e].rate;
}).reduce((a,b)=>a/b)
}
convert(amount, from, to) {
this.amount = amount;
this.fromIndex = this.data_array.findIndex(item => item.unit === from);
this.toIndex = this.data_array.findIndex(item => item.unit === to);
this.fromRate = this.data_array[this.fromIndex].rate;
this.toRate = this.data_array[this.toIndex].rate;
// higher to lower
let convertedAmount = this.fromIndex > this.toIndex ? this.amount * this.toRate : this.amount / this.fromRate;
let otherIndexes = this.findIndexNumbersBetween();
if(otherIndexes.length > 0){
convertedAmount = this.fromIndex > this.toIndex ? this.multiplyOtherIndexes(otherIndexes) : this.divideOtherIndexes(otherIndexes);
}
return this.formatAmount(convertedAmount)
}
formatAmount(convertedAmount){
if(this.in_decimal){
return Number(convertedAmount.toFixed(this.decimal_count));
}
return Number(this.countDecimal(convertedAmount));
}
}
const cunit = new CUnit(data_array,{in_decimal:true,decimal_count:5});
console.log(cunit.convert(12, "pack", "box")) // 0.1const cunit = new CUnit(data_array,{in_decimal:true,decimal_count:5});
console.log(cunit.convert(12, "pack", "box")) // 0.1
console.log(cunit.convert(1, "cigaratte", "cartoon")) // 0.00417
console.log(cunit.convert(12, "cartoon", "pack")) // 144
console.log(cunit.convert(1, "pack", "cigaratte")) // 20
console.log(cunit.convert(2, "box", "cigaratte")) // 4800| option | type | default | available values | description |
|---|---|---|---|---|
| in_decimal | boolean | false | true/false | we can use in_decimal when we what the output with decimals e.g instead of 1, it'll output 1.05 |
| decimal_count | number | 2 | 0 to 10 | It's the same with js's toFixed . E.g if we set 4 , it'll show 4 decimals 0.0245 |