Copyright © 2005 Suradet Jitprapaikulsarn
สงวนลิขสิทธิ์ 2548 สุรเดช จิตประไพกุลศาล

Homework 11 (Due 5 September 2005)

1. Write a function, calcTax, to calculate the tax using the table

Year income

Rate

<= 100,000

0%

100,000 < income <= 500,000

12%

500,000< income <= 1,000,000

15%

1,000,000 < income <= 5,000,000

23%

> 5,000,000

28%

For instance, if the income is 3,500,000 then the tax = 500,000 x 12% +  500,000 x 15% + 2,500,000 x 23% = 710,000

            C Solution

//--------------------------------------------------------------------------
// @description calculate the tax from the income
//              income                  rate
//              <= 100,000                0%
//      100,000 < income <= 500,000      12%
//      500,000 < income <= 1,000,000    15%
//    1,000,000 < income <= 5,000,000    23%
//              > 5,000,000              28%
// @param income the individual income
// @return the tax
// @contract calcTax : double -> double
// @example calcTax(90000.0)   == 0.0
// @example calcTax(120000.0)  == 2400
// @example calcTax(750000.0)  == 85500.0
// @example calcTax(3500000.0) == 698000.0
// @example calcTax(9000000.0) == 2163000.0
//--------------------------------------------------------------------------
double calcTax(double income)
{
    if (income <= 100000.0)
    {
        return 0.0;
    }
    else if (income <= 500000.0)
    {
        return (income - 100000.0) * 0.12;
    }
    else if (income <= 1000000.0)
    {
        return (income - 500000.0) * 0.15 + 48000;
    }
    else if (income <= 5000000.0)
    {
        return (income - 1000000.0) * 0.23 + 123000.0;
    }
    else
    {
        return (income - 5000000.0) * 0.28 + 1043000.0;
    }
}

           Scheme Solution

;----------------------------------------------------------------------------
; @description calculate the tax from the income
;              income                  rate
;              <= 100,000                0%
;      100,000 < income <= 500,000      12%
;      500,000 < income <= 1,000,000    15%
;    1,000,000 < income <= 5,000,000    23%
;              > 5,000,000              28%
; @param income the individual income
; @return the tax
; @contract calcTax : double -> double
; @example (calcTax 90000.0)   == 0.0
; @example (calcTax 120000.0)  == 2400
; @example (calcTax 750000.0)  == 85500.0
; @example (calcTax 3500000.0) == 698000.0
; @example (calcTax 9000000.0) == 2163000.0
;----------------------------------------------------------------------------
(define (calcTax income)
  (cond
    [(<= income 100000) 0]
    [(<= income 500000) (* (- income 100000) 0.12)]
    [(<= income 1000000) (+ (* (- income 500000) 0.15) 48000)]
    [(<= income 5000000) (+ (* (- income 1000000) 0.23) 123000)]
    [else (+ (* (- income 5000000) 0.28) 1043000)]))

2. Write the data definition of date to represent. (วัน เดือน ปี)

     - C definition / data example / code pattern

//--------------------------------------------------------------------------
// Data Definition
// ---------------
//  A date is a structure consisting of
//      - day as number
//      - month as number
//      - year as number
//--------------------------------------------------------------------------
struct Date
{
    int day;
    int month;
    int year;
};

//--------------
// Data Example
//--------------
Date date_1 = {  3, 4, 1900 };
Date date_2 = {  2, 7, 1945 };
Date date_3 = { 12, 4, 1996 };
Date date_4 = {  9, 5, 2000 };

//--------------
// Code Pattern
//--------------
// ... F(Date d)
// {
//     ... d.day ...
//     ... d.month ...
//     ... d.year ...
// }

     - Scheme definition / data example / code pattern

;----------------------------------------------------------------------------
; Data Definition
; ---------------
; A date is a structure consisting of
;    - day as number
;    - month as number
;    - year as number
;----------------------------------------------------------------------------
(define-struct date (day month year))

;--------------
; Data Example
;--------------
(define date-1 (make-date  3 4 1900))
(define date-2 (make-date  2 7 1945))
(define date-3 (make-date 12 4 1996))
(define date-4 (make-date  9 5 2000))

;-------------
; Code Pattern
; ------------
;(define (F d)
;  ... (date-day d) ...
;  ... (date-month d) ...
;  ... (date-year d) ...
;******************************************************************************

  1. Write a function, isLeapyear, to check if a year is a leaps year. A leap year is a year which February has 29 days.

        Hint:

             5 % 2   == 1         and     (remainder 5 2)  = 1

             10 % 7 == 3         and     (remainder 10 7) = 3

             21 % 4 == 1         and     (remainder 21 4) = 1

           C Soluion

//--------------------------------------------------------------------------
// @description check whether a year is a leap year
// @param d a date
// @return true if d is a leap year, false otherwise
// @contract isLeapYear : Date -> boolean
// @example isLeapYear(date_1) == false
// @example isLeapYear(date_2) == false
// @example isLeapYear(date_3) == true
// @example isLeapYear(date_4) == true
//--------------------------------------------------------------------------
bool isLeapYear(Date d)
{
    return ((d.year % 400) == 0) ||
           (((d.year % 100) != 0) && ((d.year % 4) == 0));
}

          Scheme Solution

;----------------------------------------------------------------------------
; @description check whether a year is a leap year
; @param d a date
; @return true if d has a leap year, false otherwise
; @contract isLeapYear : date -> boolean
; @example (isLeapYear date-1) = false
; @example (isLeapYear date-2) = false
; @example (isLeapYear date-3) = true
; @example (isLeapYear date-4) = true
;----------------------------------------------------------------------------
(define (isLeapYear d)
  (cond
    [(= (remainder (date-year d) 400) 0) true]
    [(= (remainder (date-year d) 100) 0) false]
    [(= (remainder (date-year d) 4) 0) true]
    [else false]))

  1. Write a function, nDay, to calculate the number of days since new year.
          C Soluion
//--------------------------------------------------------------------------
// @description calculate the leap day
// @param d a date
// @return 1 if d is a leap year, 0 otherwise
// @contract leapDay : Date -> int
// @example leapDay(date_1) == 0
// @example leapDay(date_2) == 0
// @example leapDay(date_3) == 1
// @example leapDay(date_4) == 1
//--------------------------------------------------------------------------
int leapDay(Date d)
{
    if (isLeapYear(d))
        return 1;
    else
        return 0;
}

//--------------------------------------------------------------------------
// @description calculate the number of days since the new year
// @param d a date
// @return the number of days since the new year
// @contract nDay : Date -> number
// @example nDay(date_1) == 31 + 28 + 31 + 3 == 93
// @example nDay(date_2) == 31 + 28 + 31 + 30 + 31 + 31 + 2 = 184
// @example nDay(date_3) == 31 + 29 + 31 + 12 == 103
// @example nDay(date_4) == 31 + 29 + 31 + 30 + 9 == 130
//--------------------------------------------------------------------------
int nDay(Date d)
{
    if (d.month == 1)
        return d.day;
    else if (d.month == 2)
        return 31 + d.day;
    else if (d.month == 3)
        return 31 + 28 + d.day + leapDay(d);
    else if (d.month == 4)
        return 31 + 28 + 31 + d.day + leapDay(d);
    else if (d.month == 5)
        return 31 + 28 + 31 + 30 + d.day + leapDay(d);
    else if (d.month == 6)
        return 31 + 28 + 31 + 30 + 31 + d.day + leapDay(d);
    else if (d.month == 7)
        return 31 + 28 + 31 + 30 + 31 + 31 + d.day + leapDay(d);
    else if (d.month == 8)
        return 31 + 28 + 31 + 30 + 31 + 31 + 31 + d.day + leapDay(d);
    else if (d.month == 9)
        return 31 + 28 + 31 + 30 + 31 + 31 + 31 + 31 + d.day + leapDay(d);
    else if (d.month == 10)
        return 31 + 28 + 31 + 30 + 31 + 31 + 31 + 31 + 30 + d.day + leapDay(d);
    else if (d.month == 11)
        return 31 + 28 + 31 + 30 + 31 + 31 + 31 + 31 + 30 + 31 + d.day + leapDay(d);
    else
        return 31 + 28 + 31 + 30 + 31 + 31 + 31 + 31 + 30 + 31 + 30 + d.day + leapDay(d);
}

          Scheme Solution

;----------------------------------------------------------------------------
; @description calculate the leap day
; @param d a date
; @return 1 if d is a leap year, 0 otherwise
; @contract leapDay : date -> Number
; @example (leapDay date_1) == 0
; @example (leapDay date_2) == 0
; @example (leapDay date_3) == 1
; @example (leapDay date_4) == 1
;----------------------------------------------------------------------------
(define (leapDay d)
  (cond
    [(isLeapYear d) 1]
    [else 0]))


;----------------------------------------------------------------------------
; @description calculate the number of days since the new year
; @param d a date
; @return the number of days since the new year
; @contract nDay : date -> number
; @example (nDay date_1) == 31 + 28 + 31 + 3 == 93
; @example (nDay date_2) == 31 + 28 + 31 + 30 + 31 + 31 + 2 = 184
; @example (nDay date_3) == 31 + 29 + 31 + 12 == 103
; @example (nDay date_4) == 31 + 29 + 31 + 30 + 9 == 130
;----------------------------------------------------------------------------
(define (nDay d)
  (cond
    [(= (date-month d) 1) (date-day d)]
    [(= (date-month d) 2) (+ 31 (date-day d))]
    [(= (date-month d) 3) (+ 31 28 (leapDay d) (date-day d))]
    [(= (date-month d) 4) (+ 31 28 31 (leapDay d)  (date-day d))]
    [(= (date-month d) 5) (+ 31 28 31 30 (leapDay d)  (date-day d))]
    [(= (date-month d) 6) (+ 31 28 31 30 31 (leapDay d)  (date-day d))]
    [(= (date-month d) 7) (+ 31 28 31 30 31 31 (leapDay d)  (date-day d))]
    [(= (date-month d) 8) (+ 31 28 31 30 31 31 31 (leapDay d)  (date-day d))]
    [(= (date-month d) 9) (+ 31 28 31 30 31 31 31 31 (leapDay d)  (date-day d))]
    [(= (date-month d) 10) (+ 31 28 31 30 31 31 31 31 30 (leapDay d)  (date-day d))]
    [(= (date-month d) 11) (+ 31 28 31 30 31 31 31 31 30 31 (leapDay d)  (date-day d))]
    [(= (date-month d) 12) (+ 31 28 31 30 31 31 31 31 30 31 30 (leapDay d)  (date-day d))]))