Вычислить среднее значение вложенной коллекции ⇐ Php
Вычислить среднее значение вложенной коллекции
I do have a collection and I want to do either one of the following: the sum or the average of a property in specific relation in that collection so for example I want to get the average from the total property in the following relation orders.invoice so in the code I have to loop on all the orders (as the orders here are an array) and then go to each invoice (as the order here has one invoice) in each order and then calculate the average. so if we have 3 orders and those orders has an invoice with those values (in the total property) 50, 200 and 100, the return value will be (50 + 200 + 100) / 3 = 116.7 if we are doing an average if we are doing sum it would be 50 + 200 + 100 = 350
note that the collection could be nested and we don't know the type of the relation between the nested relations ex: "relation1.relation2.relatoin3" so if relation 1 is a collection we will need to loop on it and if relation2 is an object we just go directly to the next relation.
so far I have managed to do the sum but what's left is the average, here is the function:
/** * calculate the sum/AVG based on the chosen property on a single relation or nested relations. * * @var \Illuminate\Support\Collection | array $entity * @var string $path * @var string $property * @var 'sum'|'avg' $operation * @return float */ public static function compute($entity, string $path, string $property, string $operation = 'sum'): float { $parts = explode('.', $path, 2); // Limit to 2 parts $relation = $parts[0]; $new_path = isset($parts[1]) ? $parts[1] : ''; $result = 0; $count = 0; if (is_iterable($entity)) { $entity->each(function ($item) use (&$result, &$count, $path, $property, $operation) { $result += self::compute($item, $path, $property, $operation); $count++; }); return $result; } if (is_iterable($entity->{$relation})) { collect($entity->{$relation})->each(function ($item) use (&$result, &$count, $new_path, $property, $operation) { if($new_path == '') { $result += $item->{$property}; $count++; } else { $result += self::compute($item, $new_path, $property, $operation); } }); } else if($entity->{$relation}) { if($new_path == '') { $result += $entity->{$relation}->{$property}; $count++; } else { $result += self::compute($entity->{$relation}, $new_path, $property, $operation); } } if($operation == 'avg' && $count > 0) { // dd($count); $result /= 4; // here is the problem in the `avg` as we can't save the value of the $count on every function call as we do with $result } return $result; } here is the test:
Источник: https://stackoverflow.com/questions/781 ... collection
I do have a collection and I want to do either one of the following: the sum or the average of a property in specific relation in that collection so for example I want to get the average from the total property in the following relation orders.invoice so in the code I have to loop on all the orders (as the orders here are an array) and then go to each invoice (as the order here has one invoice) in each order and then calculate the average. so if we have 3 orders and those orders has an invoice with those values (in the total property) 50, 200 and 100, the return value will be (50 + 200 + 100) / 3 = 116.7 if we are doing an average if we are doing sum it would be 50 + 200 + 100 = 350
note that the collection could be nested and we don't know the type of the relation between the nested relations ex: "relation1.relation2.relatoin3" so if relation 1 is a collection we will need to loop on it and if relation2 is an object we just go directly to the next relation.
so far I have managed to do the sum but what's left is the average, here is the function:
/** * calculate the sum/AVG based on the chosen property on a single relation or nested relations. * * @var \Illuminate\Support\Collection | array $entity * @var string $path * @var string $property * @var 'sum'|'avg' $operation * @return float */ public static function compute($entity, string $path, string $property, string $operation = 'sum'): float { $parts = explode('.', $path, 2); // Limit to 2 parts $relation = $parts[0]; $new_path = isset($parts[1]) ? $parts[1] : ''; $result = 0; $count = 0; if (is_iterable($entity)) { $entity->each(function ($item) use (&$result, &$count, $path, $property, $operation) { $result += self::compute($item, $path, $property, $operation); $count++; }); return $result; } if (is_iterable($entity->{$relation})) { collect($entity->{$relation})->each(function ($item) use (&$result, &$count, $new_path, $property, $operation) { if($new_path == '') { $result += $item->{$property}; $count++; } else { $result += self::compute($item, $new_path, $property, $operation); } }); } else if($entity->{$relation}) { if($new_path == '') { $result += $entity->{$relation}->{$property}; $count++; } else { $result += self::compute($entity->{$relation}, $new_path, $property, $operation); } } if($operation == 'avg' && $count > 0) { // dd($count); $result /= 4; // here is the problem in the `avg` as we can't save the value of the $count on every function call as we do with $result } return $result; } here is the test:
Источник: https://stackoverflow.com/questions/781 ... collection
-
- Похожие темы
- Ответы
- Просмотры
- Последнее сообщение
-
-
Вычислить среднее значение группы для столбца int_range в кадре данных Polars
Anonymous » » в форуме Python - 0 Ответы
- 20 Просмотры
-
Последнее сообщение Anonymous
-
-
-
Вычислить среднее значение значений в списке, сгруппированном по меткам
Anonymous » » в форуме Python - 0 Ответы
- 23 Просмотры
-
Последнее сообщение Anonymous
-