Camel
Peter
Peter Campbell Smith

Counts and discounts

Weekly challenge 325 — 9 June 2025

Week 325: 9 Jun 2025

Task 2

Task — Final price

You are given an array of item prices. Write a script to find out the final price of each items in the given array. There is a special discount scheme going on. If there’s an item with a lower or equal price later in the list, you get a discount equal to that later price (the first one you find in order).

Examples


Example 1
Input: @prices = (8, 4, 6, 2, 3)
Output: (4, 2, 4, 2, 3)
Item 0:
The item price is 8.
The first time that has price <= current item price is 
   4.
Final price = 8 - 4 => 4
Item 1:
The item price is 4.
The first time that has price <= current item price is 
   2.
Final price = 4 - 2 => 2
Item 2:
The item price is 6.
The first time that has price <= current item price is 
   2.
Final price = 6 - 2 => 4
Item 3:
The item price is 2.
No item has price <= current item price, no discount.
Final price = 2
Item 4:
The item price is 3.
Since it is the last item, so no discount.
Final price = 3

Example 2
Input: @prices = (1, 2, 3, 4, 5)
Output: (1, 2, 3, 4, 5)

Example 3
Input: @prices = (7, 1, 1, 5)
Output: (6, 0, 1, 5)
Item 0:
The item price is 7.
The first time that has price <= current item price is 
   1.
Final price = 7 - 1 => 6
Item 1:
The item price is 1.
The first time that has price <= current item price is 
   1.
Final price = 1 - 1 => 0
Item 2:
The item price is 1.
No item has price <= current item price,
   so no discount.
Final price = 1
Item 3:
The item price is 5.
Since it is the last item, so no discount.
Final price = 5

Analysis

This is an interesting commercial strategy. The John Lewis chain in the UK offers to match any price set by a competitor, but this challenge goes further and, if I may offer some advice, is not optimal for financial success. Your competitors need only match your prices, at which point you will be giving everything away for free and will go bust. They can then charge what they like.

However, undeterred, I present a solution. It's really just a translation of the challenge text into Perl. Loop over the given prices, and for each one, loop over the subsequent ones, looking for an equal or lower price. If you find one, subtract it from the target price; if you don't, leave the target price unchanged.

But don't say I didn't warn you.

Try it 

Try running the script with any input:



example: 5, 6, 7, 5, 6, 7

Script


#!/usr/bin/perl

# Blog: http://ccgi.campbellsmiths.force9.co.uk/challenge

use v5.26;    # The Weekly Challenge - 2025-06-09
use utf8;     # Week 325 - task 2 - Final price
use warnings; # Peter Campbell Smith
binmode STDOUT, ':utf8';
use Encode;

final_price(8, 4, 6, 2, 3);
final_price(1, 2, 3, 4, 5);
final_price(7, 1, 1, 5);
final_price(3);
final_price(7, 7, 7, 7, 7);

sub final_price {
    
    my(@prices, $j, $k);
    
    # initialise
    @prices = @_;
    say qq[\nInput:  (] . join(', ', @prices) . q[)];
    
    # check each price (except the last)
    J: for $j (0 .. $#prices - 1) {
        
        # look over subsequent prices
        for $k ($j + 1 .. $#prices) {
            
            # found a discounting one
            if ($prices[$k] <= $prices[$j]) {
                $prices[$j] -= $prices[$k];
                next J;
            }
        }
    }           
    say qq[Output: (] . join(', ', @prices) . q[)];
}

Output


Input:  (8, 4, 6, 2, 3)
Output: (4, 2, 4, 2, 3)

Input:  (1, 2, 3, 4, 5)
Output: (1, 2, 3, 4, 5)

Input:  (7, 1, 1, 5)
Output: (6, 0, 1, 5)

Input:  (3)
Output: (3)

Input:  (7, 7, 7, 7, 7)
Output: (0, 0, 0, 0, 7)

 

Any content of this website which has been created by Peter Campbell Smith is in the public domain