Writing code exam questions

 ☺寫程式碼考題

影像旋轉
最大公因數及最小公倍數
照類別圖設計程式

簡單


影像的旋轉

假設有一灰階影像 img1,其類別為 Image 如下:

class Image {

private:

int width; // 寬

int height; // 高

unsigned char **pixel; // 像素

public:

Image(int w, int h); // 建構子

unsigned char getpixel(int r, int c); // 取出 pixel[r][c]值

void setpixel(int r, int c, unsigned char g);// 設定 pixel[r][c]值為 g

int getwidth(); // 取出影像的寬度

int getheight(); // 取出影像的高度

}

其寬為 width,高為 height,其像素值存在一個二維陣列 pixel 中,資料型態為 unsigned

char。今欲將此灰階影像 img1 順時針旋轉 90 度,並儲存在另一新的灰階影像 img2。

試寫出 Image 類別的建構子,依據參數 w(代表寬度)與 h(代表高度),可以動

態配置二維陣列 pixel。(10 分)

試完成 Image 類別的其他成員函式:getpixel( ),setpixel( ),getwidth( ),和

getheight( ),並寫出一個 PrtImg( )函式如下,列印影像 img 參數中 pixel 的值,其

中每一列(row)印完需跳行,像素值以空白隔開。(10 分)

void PrtImg(Image & img)

{

......

}

試寫出一個 Rotate( )函式如下,將參數 img1 順時針旋轉 90 度後,存成新的影像

img2,並回傳。(10 分)

Image Rotate(Image & img1)

{

......

}



以下是 Image 類別的完整定義:

#include <iostream>


class Image {

private:

    int width; // 寬

    int height; // 高

    unsigned char **pixel; // 像素


public:

    Image(int w, int h) : width(w), height(h) {

        pixel = new unsigned char*[height];

        for (int i = 0; i < height; i++) {

            pixel[i] = new unsigned char[width];

        }

    }


    ~Image() {

        for (int i = 0; i < height; i++) {

            delete[] pixel[i];

        }

        delete[] pixel;

    }


    unsigned char getpixel(int r, int c) {

        return pixel[r][c];

    }


    void setpixel(int r, int c, unsigned char g) {

        pixel[r][c] = g;

    }


    int getwidth() {

        return width;

    }


    int getheight() {

        return height;

    }

};


void PrtImg(Image & img) {

    for (int i = 0; i < img.getheight(); i++) {

        for (int j = 0; j < img.getwidth(); j++) {

            std::cout << static_cast<int>(img.getpixel(i, j)) << " ";

        }

        std::cout << std::endl;

    }

}


Image Rotate(Image & img1) {

    Image img2(img1.getheight(), img1.getwidth());

    for (int i = 0; i < img1.getheight(); i++) {

        for (int j = 0; j < img1.getwidth(); j++) {

            img2.setpixel(j, img1.getheight() - 1 - i, img1.getpixel(i, j));

        }

    }

    return img2;

}


在上述程式碼中,我們定義了一個 Image 類別,其包含有寬度 width、高度 height 和像素值 pixel。在建構子中,我們使用 new 運算子動態配置二維陣列 pixel。在解構子中,我們使用 delete 運算子釋放動態配置的記憶體。

我們使用了成員函式 getpixel() 和 setpixel() 分別取出和設定像素值。在成員函式 getwidth() 和 getheight() 中,我們分別取出影像的寬度和高度。

在函式 PrtImg() 中,我們使用兩層迴圈來列印影像中的像素值。在函式 Rotate() 中,我們建立了一個新的影像物件 img2,並將參數影像 img1 順時針旋轉 90 度後存入其中。

最大公因數及最小公倍數

試以 C++來定義有理數(意即分數)類別 Rational 如下,其包含有分子 a 和分母 b,其

中分母 b 不能為 0。

class Rational {

private:

int a; // 分子

int b; // 分母

......

public:

......

};

假設 main( )的主程式,和其所執行輸出的結果如下:

Rational r0;

cout << "r0 = "; r0.prt( );

Rational r1(2, 4);

Rational r2(3, 6);

cout << "r1 = "; r1.prt( );

cout << "r2 = "; r2.prt( );

Rational r3 = r1+r2;

Rational r4 = r1-r2;

Rational r5 = r1*r2;

Rational r6 = r1/r2;

cout << "r1 + r2 = "; r3.prt( );

cout << "r1 - r2 = "; r4.prt( );

cout << "r1 * r2 = "; r5.prt( );

cout << "r1 / r2 = "; r6.prt( );

輸出結果:

r0 = 0/1

r1 = 1/2

r2 = 1/2

r1 + r2 = 1/1

r1 - r2 = 0/1

r1 * r2 = 1/4

r1 / r2 = 1/1

試列出完整的 Rational 類別定義。(10 分)

試完成所需的建構子(包含預設建構子),多載運算子(overloaded operators):加、

減、乘、除等,以及成員函式 prt( ),和相關的程式碼。注意:有理數輸出必須為

最簡分數,並藉機將有理數化簡成最簡分數。(20 分)


以下是 Rational 類別的完整定義:

#include <iostream>

#include <numeric>


class Rational {

private:

    int a; // 分子

    int b; // 分母


public:

    Rational() : a(0), b(1) {}

    Rational(int a, int b) : a(a), b(b) {}


    void prt() const {

        std::cout << a << "/" << b << std::endl;

    }


    friend Rational operator+(const Rational& r1, const Rational& r2) {

        int lcm = std::lcm(r1.b, r2.b);

        int numerator = r1.a * (lcm / r1.b) + r2.a * (lcm / r2.b);

        return Rational(numerator / std::gcd(numerator, lcm), lcm / std::gcd(numerator, lcm));

    }


    friend Rational operator-(const Rational& r1, const Rational& r2) {

        int lcm = std::lcm(r1.b, r2.b);

        int numerator = r1.a * (lcm / r1.b) - r2.a * (lcm / r2.b);

        return Rational(numerator / std::gcd(numerator, lcm), lcm / std::gcd(numerator, lcm));

    }


    friend Rational operator*(const Rational& r1, const Rational& r2) {

        return Rational(r1.a * r2.a / std::gcd(r1.a * r2.a, r1.b * r2.b), r1.b * r2.b / std::gcd(r1.a * r2.a, r1.b * r2.b));

    }


    friend Rational operator/(const Rational& r1, const Rational& r2) {

        return Rational(r1.a * r2.b / std::gcd(r1.a * r2.b, r1.b * r2.a), r1.b * r2.a / std::gcd(r1.a * r2.b, r1.b * r2.a));

    }

};


在上述程式碼中,我們定義了一個 Rational 類別,其包含有分子 a 和分母 b。我們使用了 C++11 的 std::lcm 和 std::gcd 函式來求最小公倍數和最大公因數。在 prt() 函式中,我們將有理數以最簡分數的形式輸出。

我們使用了運算子重載來實現加、減、乘、除等運算。在運算時,我們先求出兩個有理數的最小公倍數,然後將分子相加、相減、相乘、相除,再將結果化簡成最簡分數。

以下是 main() 函式的程式碼:

int main() {

    Rational r0;

    std::cout << "r0 = "; 

    r0.prt();


    Rational r1(2, 4);

    Rational r2(3, 6);

    std::cout << "r1 = "; 

    r1.prt();

    std::cout << "r2 = "; 

    r2.prt();


    Rational r3 = r1 + r2;

    Rational r4 = r1 - r2;

    Rational r5 = r1 * r2;

    Rational r6 = r1 / r2;


    std::cout << "r1 + r2 = "; 

    r3.prt();

    std::cout << "r1 - r2 = "; 

    r4.prt();

    std::cout << "r1 * r2 = "; 

    r5.prt();

    std::cout << "r1 / r2 = "; 

    r6.prt();


    return 0;

}


在 main() 函式中,我們建立了四個有理數物件 r0、r1、r2、r3、r4、r5 和 r6。然後我們使用運算子重載來實現加、減、乘、除等運算,並將結果輸出為最簡分數

照類別圖設計程式

要點

  • 如何用java enum
  • 如何取得java現在時間
  • 如何用list資料結構新增資料,與iterate
  • 重寫override 

請使用物件導向程式語言(C#或 Java),設計一具門禁功能的智慧卡管理資訊系統。

系統應依如下的 class diagram 建立相關的類別資訊。(35 分


所有的類別變數皆為 private,SMsecurity 類別繼承自抽象類別 SmartCard

z 發卡單位 Organization、進出入狀況 EnterExit,請分別使用 enum 的格式來表示

z 記錄進出入狀況,日期資料若未提供,則填入目前系統的日期時間

z 一張智慧卡,會有多次的進出入記錄,資料值應存放於 List 線性資料結構中

z 改寫系統的 toString()方法後,執行如下的測試動作

SMsecurity sms = new SMsecurity("SM001", Organization.NewTaipeiMRT);

sms.addInfo("2015/06/15 18:36:01", EnterExit.Enter);

sms.addInfo("2015/06/15 20:16:01", EnterExit.Exit);

sms.addInfo("2015/06/20 18:20:01", EnterExit.Enter);

sms.addInfo(EnterExit.Exit);

/* for Java */ System.out.println(sms.toString());

/* for C# */ Console.WriteLine(sms.ToString());

應能產生類似如下的結果

*****Smart card SM001 (6/21/2015 10:38:38 PM, NewTaipeiMRT)

-----Enter and Exit information:

(2015/06/15 18:36:01, Enter)

(2015/06/15 20:16:01, Exit)

(2015/06/20 18:20:01, Enter)

(6/21/2015 10:38:38 PM, Exit)

答案

頁尾



Comments

Popular posts from this blog

How to write data into a excel file using vbscript

Format date as yyyy-mm-dd using vbscript