Kotlin練習問題4-☆3:アラビア数字をローマ数字に変換しよう

記事内に商品プロモーションを含む場合があります

Kotlinの初心者向け問題4-☆3:アラビア数字をローマ数字に変換しよう

この問題を解くために必要な知識:

【レベル1~3の知識】
コメントの書き方、変数と定数、基本データ型、算術演算と論理演算、入力と出力、import文、配列、分岐処理(if、if~else、when)、繰り返し処理(for、while、do~while)、Null安全、スマートキャスト、関数の定義と呼び出し、関数の戻り値、関数のオーバーロード、ラベルとジャンプ、例外処理、クラスの定義と使用、インスタンス、コンストラクタ、プロパティ、クラスの継承、クラスの拡張、コレクションの基礎、リストコレクション(MutableList、ArrayList)、セットコレクション(HashSet、MutableSet、TreeSet)、マップコレクション(HashMap、MutableMap、TreeMap)

【レベル4の知識】
メンバ関数、ゲッターとセッター、カプセル化、クラスメンバ、抽象クラス、インターフェース、データクラス

<<前の問題 問題集Top 次の問題>>

Kotlin練習問題4-☆3:アラビア数字をローマ数字に変換しよう





この課題では、アラビア数字(例: 1, 5, 10, 100)をローマ数字(例: I, V, X, C)に変換するプログラムを作成します。

具体的には、1から3999までのアラビア数字をローマ数字に変換する機能を実装します。

この問題の要件

以下の要件に従ってプログラムを完成させてください。

  1. ArabicToRomanConverter クラスを作成すること
    • このクラスは、アラビア数字をローマ数字に変換する機能を持ちます。
    • arabicValues という名前の配列に、アラビア数字の各値を大きい順に格納します(例: 1000, 900, 500, 400, …)。
    • romanNumerals という名前の配列に、arabicValues に対応するローマ数字を格納します(例: “M”, “CM”, “D”, “CD”, …)。
    • convert という名前のメンバ関数を作成し、アラビア数字をローマ数字に変換するロジックを実装します。
  2. main 関数でユーザーからの入力を受け取ること
    • main 関数でユーザーにアラビア数字を入力させ、その値をArabicToRomanConverter クラスを使ってローマ数字に変換します。
    • 入力された値が数値でない場合は、エラーメッセージを表示します。
  3. プログラムが終了するまで、ユーザーの入力を繰り返し受け付けること
    • 1回の変換後に再び入力を求めるか、プログラムを終了するかをユーザーに選ばせます。

ただし、以下のような実行結果となること。

----- ↓出力される結果の例↓ -----

アラビア数字を入力してください: 1987
ローマ数字: MCMLXXXVII

アラビア数字を入力してください: abc
無効な数値です。

----- ↑出力される結果の例↑ -----

ローマ数字の表記ルール

基本記号とその値

ローマ数字は以下の記号とその値に基づいています:

  • I = 1
  • V = 5
  • X = 10
  • L = 50
  • C = 100
  • D = 500
  • M = 1000

記号の組み合わせ

  • 基本記号は、最大で3回まで繰り返して使用できます。

例: III = 3、XXX = 30、CCC = 300

  • 通常、ローマ数字は大きな値から小さな値へと左から右に書かれます。

例: MDCLXVI = 1666(1000 + 500 + 100 + 50 + 10 + 5 + 1)

この問題を解くヒント

1からコードを組み立てることが難しい場合は、以下のヒントを開いて参考にしましょう。

ヒント1【コードの構成を見る】

正解のコードは上から順に以下のような構成となっています。

1.Randomクラスのインポート
2.ArabicToRomanConverter クラスの定義
 2-1. arabicValues 配列の定義
 2-2. romanNumerals 配列の定義
 2-3. convert メンバ関数の定義
  2-3-1. 入力されたアラビア数字を操作する変数 arabic の宣言と初期化
  2-3-2. 結果を格納する StringBuilder オブジェクト roman の作成
  2-3-3. アラビア数字をローマ数字に変換するためのループ処理
  2-3-4. StringBuilder に変換結果を追加
  2-3-5. 変換後のアラビア数字を減算
  2-3-6. 完成したローマ数字を返す
3.main 関数の定義
 3-1. ArabicToRomanConverter オブジェクトの作成
 3-2. ユーザー入力の取得
  3-2-1. アラビア数字の入力を促すメッセージの表示
  3-2-2. 入力された値の数値への変換
  3-2-3. 入力が無効な場合のエラーメッセージ表示
3-3. ローマ数字への変換と結果の表示

ヒント2【穴埋め問題にする】

以下のコードをコピーし、コメントに従ってコードを完成させて下さい。

// ArabicToRomanConverter クラス
class ArabicToRomanConverter {
    // ローマ数字の対応表
    private val arabicValues = arrayOf(1000, 900, 500, 400, 100, 90, 50, 40, 10, 9, 5, 4, 1)
    private val romanNumerals = arrayOf("M", "CM", "D", "CD", "C", "XC", "L", "XL", "X", "IX", "V", "IV", "I")

    fun convert(arabic: Int): String {
        var arabic = arabic
        val roman = StringBuilder()

        /* ***【穴埋め問題1】***
        ここにfor文を使って、arabicValuesの各値についてローマ数字を生成するコードを書いてください。
        */

        return roman.toString()
    }
}

// メイン関数
fun main() {
    val converter = ArabicToRomanConverter()

    // ユーザーにアラビア数字を入力させる
    print("アラビア数字を入力してください: ")

    /* ***【穴埋め問題2】***
    ここにユーザー入力を受け取り、それを数値に変換するコードを書いてください。
    入力が無効な場合にはエラーメッセージを表示して終了する処理も書いてください。
    */

    // ローマ数字に変換して結果を表示
    val roman = converter.convert(arabic)
    println("ローマ数字: $roman")
}

 

このヒントを見てもまだ回答を導き出すのが難しいと感じる場合は、先に正解のコードと解説を見て内容を理解するようにしましょう。

解答例

この問題の一つの正解例とそのコードの解説を以下に示します。

正解コードの例

例えば以下のようなプログラムが考えられます。

********************

// ArabicToRomanConverter クラス
class ArabicToRomanConverter {
    // ローマ数字の対応表
    private val arabicValues = arrayOf(1000, 900, 500, 400, 100, 90, 50, 40, 10, 9, 5, 4, 1)
    private val romanNumerals = arrayOf("M", "CM", "D", "CD", "C", "XC", "L", "XL", "X", "IX", "V", "IV", "I")

    fun convert(arabic: Int): String {
        var arabic = arabic
        val roman = StringBuilder()

        for (i in arabicValues.indices) {
            while (arabic >= arabicValues[i]) {
                roman.append(romanNumerals[i])
                arabic -= arabicValues[i]
            }
        }

        return roman.toString()
    }
}

// メイン関数
fun main() {
    val converter = ArabicToRomanConverter()

    // ユーザーにアラビア数字を入力させる
    print("アラビア数字を入力してください: ")
    val arabic = readLine()?.toIntOrNull() ?: run {
        println("無効な数値です。")
        return
    }

    // ローマ数字に変換して結果を表示
    val roman = converter.convert(arabic)
    println("ローマ数字: $roman")
}

********************

正解コードの解説

このコードでは、アラビア数字をローマ数字に変換するプログラムを実装しています。コードは非常にシンプルで、基本的なKotlinの文法と構造を学ぶのに適しています。

クラス ArabicToRomanConverter の定義

class ArabicToRomanConverter {
    // ローマ数字の対応表
    private val arabicValues = arrayOf(1000, 900, 500, 400, 100, 90, 50, 40, 10, 9, 5, 4, 1)
    private val romanNumerals = arrayOf("M", "CM", "D", "CD", "C", "XC", "L", "XL", "X", "IX", "V", "IV", "I")

この部分では、ArabicToRomanConverterというクラスを定義しています。このクラスは、アラビア数字をローマ数字に変換するための機能を提供します。

クラス内には、アラビア数字とそれに対応するローマ数字を保持する2つの配列arabicValuesromanNumeralsがあります。

private修飾子が使われているため、これらの配列はクラスの外部から直接アクセスすることはできません。これは「カプセル化」と呼ばれる技術で、データの不正な操作を防ぐためのものです。

2. convert 関数の定義

    fun convert(arabic: Int): String {
        var arabic = arabic
        val roman = StringBuilder()

        for (i in arabicValues.indices) {
            while (arabic >= arabicValues[i]) {
                roman.append(romanNumerals[i])
                arabic -= arabicValues[i]
            }
        }

        return roman.toString()
    }

convert関数は、アラビア数字をローマ数字に変換するためのメインロジックを持っています。この関数は、arabicという整数を受け取り、それに対応するローマ数字の文字列を返します。

  • 変数arabic: arabic変数は、受け取ったアラビア数字を格納し、その後の処理で使用されます。関数内部でvar修飾子を使って再宣言されていますが、これは元の値を変更しながら処理するためです。
  • StringBuilder クラス: romanという変数にはStringBuilderを使用しており、これにより効率的に文字列を構築できます。
  • ループ処理: forループとwhileループを組み合わせて、アラビア数字がローマ数字に変換される過程を実現しています。arabicが対応する値以上である限り、そのローマ数字が結果に追加され、アラビア数字の値が減算されます。

main 関数の定義

fun main() {
    val converter = ArabicToRomanConverter()

    // ユーザーにアラビア数字を入力させる
    print("アラビア数字を入力してください: ")
    val arabic = readLine()?.toIntOrNull() ?: run {
        println("無効な数値です。")
        return
    }

    // ローマ数字に変換して結果を表示
    val roman = converter.convert(arabic)
    println("ローマ数字: $roman")
}

main関数は、Kotlinプログラムのエントリーポイントです。ここでは、ユーザーからアラビア数字を入力させ、それをローマ数字に変換して表示するまでの処理を行います。

  • ユーザー入力: readLine()を使用してユーザーからの入力を受け取り、それを整数に変換しています。toIntOrNull()を使うことで、入力が整数に変換できなかった場合にnullを返し、nullの場合にはエラーメッセージを表示してプログラムを終了します。
  • ローマ数字への変換: ユーザーから受け取った数字をconvert関数に渡し、その結果を表示します。

まとめ

このプログラムでは、基本的なクラス定義、配列の操作、文字列の操作、ユーザー入力の処理など、Kotlinの基本的な文法を学ぶことができます。

また、カプセル化やエラー処理などの重要なプログラミング技術についても理解を深めることができます。

プログラム全体がシンプルでありながら実用的な機能を持つため、初心者にとって非常に有用な学習素材となっています。

<<前の問題 問題集Top 次の問題>>

この問題への質問・コメント

この問題を作成するにあたりAIを活用しています。

問題ないことは確認していますが、もし間違いや表現の違和感などありましたら、ご指摘頂けると大変助かります。






    Kotlin練習問題集へ戻る
    トップページへ戻る