|
| 1 | +use std::env; |
| 2 | +use std::process; |
| 3 | + |
| 4 | +// 五格を計算する構造体 |
| 5 | +struct FiveGrades { |
| 6 | + celestial: usize, |
| 7 | + human: usize, |
| 8 | + earth: usize, |
| 9 | + external: usize, |
| 10 | + total: usize, |
| 11 | +} |
| 12 | + |
| 13 | +// 五格ごとの吉凶判定結果を格納 |
| 14 | +struct GradeFortunes { |
| 15 | + celestial: String, |
| 16 | + human: String, |
| 17 | + earth: String, |
| 18 | + external: String, |
| 19 | + total: String, |
| 20 | +} |
| 21 | + |
| 22 | +// 占いの結果をより詳細に表示する構造体 |
| 23 | +struct Fortune { |
| 24 | + grades: FiveGrades, |
| 25 | + grade_fortunes: GradeFortunes, |
| 26 | + family_luck: String, |
| 27 | + gender_insights: String, |
| 28 | +} |
| 29 | + |
| 30 | +// 画数から吉凶を判定する関数 |
| 31 | +fn get_fortune_by_number(number: usize) -> String { |
| 32 | + match number { |
| 33 | + // 大吉数 |
| 34 | + 1 | 3 | 5 | 8 | 13 | 15 | 16 | 21 | 23 | 24 | 25 | 31 | 32 | 33 | 35 | 37 | 39 | 41 |
| 35 | + | 45 | 47 | 48 | 52 | 57 | 61 | 63 | 65 | 67 | 68 | 81 => "大吉".to_string(), |
| 36 | + // 吉数 |
| 37 | + 6 | 7 | 17 | 18 | 27 | 29 | 30 | 38 | 42 | 43 | 55 | 58 | 62 | 64 | 66 | 69 | 71 | 73 |
| 38 | + | 75 => "吉".to_string(), |
| 39 | + // 凶数 |
| 40 | + 4 | 10 | 12 | 14 | 20 | 22 | 26 | 34 | 36 | 40 | 44 | 46 | 49 | 50 | 51 | 53 | 54 | 56 |
| 41 | + | 59 | 60 | 70 | 72 | 74 | 76 | 77 | 78 | 79 | 80 => "凶".to_string(), |
| 42 | + // 大凶数 |
| 43 | + 9 | 11 | 19 | 28 => "大凶".to_string(), |
| 44 | + // その他の画数 |
| 45 | + _ => "吉凶不明".to_string(), |
| 46 | + } |
| 47 | +} |
| 48 | +// 吉凶を示す数値から対応する文字列に変換する関数 |
| 49 | +fn get_fortune_string(fortune_type: &usize) -> String { |
| 50 | + match *fortune_type { |
| 51 | + 1 => "大吉".to_string(), |
| 52 | + 2 => "吉".to_string(), |
| 53 | + 3 => "凶".to_string(), |
| 54 | + 4 => "大凶".to_string(), |
| 55 | + _ => "吉凶不明".to_string(), |
| 56 | + } |
| 57 | +} |
| 58 | + |
| 59 | +// 姓名判断の五格を計算する関数 |
| 60 | +fn calculate_five_grades(last_names: &[usize], first_names: &[usize]) -> FiveGrades { |
| 61 | + let last_name_total: usize = last_names.iter().sum(); |
| 62 | + let first_name_total: usize = first_names.iter().sum(); |
| 63 | + let celestial = last_name_total; |
| 64 | + let human = last_names.last().unwrap_or(&0) + first_names.first().unwrap_or(&0); |
| 65 | + let earth = first_name_total; |
| 66 | + let total = last_name_total + first_name_total; |
| 67 | + let external = total - human; |
| 68 | + FiveGrades { |
| 69 | + celestial, |
| 70 | + human, |
| 71 | + earth, |
| 72 | + external, |
| 73 | + total, |
| 74 | + } |
| 75 | +} |
| 76 | + |
| 77 | +// 五格、家庭運、性別に基づいた運勢を診断する関数 |
| 78 | +fn diagnose_fortune(grades: &FiveGrades, is_male: bool) -> Fortune { |
| 79 | + let mut family_luck = String::new(); |
| 80 | + let mut gender_insights = String::new(); |
| 81 | + |
| 82 | + match get_fortune_by_number(grades.human).as_str() { |
| 83 | + "大吉" | "吉" => family_luck |
| 84 | + .push_str("人格が吉数であり、配偶者との関係は良好です。円満な家庭を築けるでしょう。"), |
| 85 | + _ => family_luck |
| 86 | + .push_str("人格が不安定なため、家庭内でのコミュニケーションを心がけましょう。"), |
| 87 | + } |
| 88 | + |
| 89 | + if is_male { |
| 90 | + gender_insights.push_str("男性の場合、人格や総格が仕事運や社会的な成功に強く影響します。"); |
| 91 | + } else { |
| 92 | + gender_insights |
| 93 | + .push_str("女性の場合、地格が独身時代の運勢や才能を、総格が晩年の家庭運を左右します。"); |
| 94 | + } |
| 95 | + |
| 96 | + let grade_fortunes = GradeFortunes { |
| 97 | + celestial: get_fortune_by_number(grades.celestial), |
| 98 | + human: get_fortune_by_number(grades.human), |
| 99 | + earth: get_fortune_by_number(grades.earth), |
| 100 | + external: get_fortune_by_number(grades.external), |
| 101 | + total: get_fortune_by_number(grades.total), |
| 102 | + }; |
| 103 | + |
| 104 | + Fortune { |
| 105 | + grades: FiveGrades { ..*grades }, |
| 106 | + grade_fortunes, |
| 107 | + family_luck, |
| 108 | + gender_insights, |
| 109 | + } |
| 110 | +} |
| 111 | + |
| 112 | +// 引数からusizeのVecを解析するヘルパー関数 |
| 113 | +fn parse_usize_vec(arg: &str) -> Vec<usize> { |
| 114 | + arg.split(',') |
| 115 | + .filter_map(|s| s.trim().parse::<usize>().ok()) |
| 116 | + .collect() |
| 117 | +} |
| 118 | + |
| 119 | +// 引数の使い方を表示するヘルパー関数 |
| 120 | +fn print_usage() { |
| 121 | + println!("使い方:"); |
| 122 | + println!(" 診断モード: cargo run diagnose <名字の画数(カンマ区切り)> <名前の画数(カンマ区切り)> [male]"); |
| 123 | + println!(" 例: cargo run -- diagnose 3,5 7,3"); |
| 124 | + println!(" 例: cargo run -- diagnose 3,5 4,9 male"); |
| 125 | + println!(" 画数検索モード: cargo run lookup <celestial_fortune> <human_fortune> <earth_fortune> <external_fortune> <total_fortune> <max>"); |
| 126 | + println!(" <fortune> : 吉凶を示す数値 (1=大吉, 2=吉, 3=凶, 4=大凶, 0=任意)"); |
| 127 | + println!(" <max> : 最大検索件数 (例: 10)"); |
| 128 | + println!(" 例: 全て大吉の組み合わせを検索 -> cargo run -- lookup 1 1 1 1 1 10"); |
| 129 | + println!( |
| 130 | + " 例: 人格と総格が大吉で、他は任意の組み合わせ -> cargo run -- lookup 0 1 0 0 1 10" |
| 131 | + ); |
| 132 | +} |
| 133 | + |
| 134 | +// main関数 |
| 135 | +fn main() { |
| 136 | + let args: Vec<String> = env::args().collect(); |
| 137 | + |
| 138 | + if args.len() < 2 { |
| 139 | + print_usage(); |
| 140 | + process::exit(1); |
| 141 | + } |
| 142 | + |
| 143 | + let command = &args[1]; |
| 144 | + |
| 145 | + match command.as_str() { |
| 146 | + "diagnose" => { |
| 147 | + if args.len() < 4 { |
| 148 | + eprintln!("エラー: 診断モードには名字と名前の画数が必要です。"); |
| 149 | + print_usage(); |
| 150 | + process::exit(1); |
| 151 | + } |
| 152 | + |
| 153 | + let last_names = parse_usize_vec(&args[2]); |
| 154 | + let first_names = parse_usize_vec(&args[3]); |
| 155 | + let is_male = args.get(4).map(|s| s == "male").unwrap_or(false); |
| 156 | + |
| 157 | + if last_names.is_empty() || first_names.is_empty() { |
| 158 | + eprintln!("エラー: 正しい画数が入力されていません。"); |
| 159 | + print_usage(); |
| 160 | + process::exit(1); |
| 161 | + } |
| 162 | + |
| 163 | + let grades = calculate_five_grades(&last_names, &first_names); |
| 164 | + let fortune = diagnose_fortune(&grades, is_male); |
| 165 | + |
| 166 | + println!("--- 姓名判断の結果 ---"); |
| 167 | + println!( |
| 168 | + "天格 (名字の総画数): {} ({})", |
| 169 | + fortune.grades.celestial, fortune.grade_fortunes.celestial |
| 170 | + ); |
| 171 | + println!( |
| 172 | + "人格 (内面の性格): {} ({})", |
| 173 | + fortune.grades.human, fortune.grade_fortunes.human |
| 174 | + ); |
| 175 | + println!( |
| 176 | + "地格 (基礎運): {} ({})", |
| 177 | + fortune.grades.earth, fortune.grade_fortunes.earth |
| 178 | + ); |
| 179 | + println!( |
| 180 | + "外格 (対人関係): {} ({})", |
| 181 | + fortune.grades.external, fortune.grade_fortunes.external |
| 182 | + ); |
| 183 | + println!( |
| 184 | + "総格 (一生の運勢): {} ({})", |
| 185 | + fortune.grades.total, fortune.grade_fortunes.total |
| 186 | + ); |
| 187 | + |
| 188 | + println!("\n--- 詳細な運勢 ---"); |
| 189 | + println!("家庭運: {}", fortune.family_luck); |
| 190 | + println!("性別ごとの診断: {}", fortune.gender_insights); |
| 191 | + } |
| 192 | + "lookup" => { |
| 193 | + if args.len() != 8 { |
| 194 | + eprintln!("エラー: 検索モードには5つの吉凶タイプと最大検索数が必要です。"); |
| 195 | + print_usage(); |
| 196 | + process::exit(1); |
| 197 | + } |
| 198 | + |
| 199 | + let celestial_type: usize = args[2].parse().unwrap_or_else(|_| { |
| 200 | + eprintln!("エラー: 天格の吉凶が不正です。"); |
| 201 | + process::exit(1); |
| 202 | + }); |
| 203 | + let human_type: usize = args[3].parse().unwrap_or_else(|_| { |
| 204 | + eprintln!("エラー: 人格の吉凶が不正です。"); |
| 205 | + process::exit(1); |
| 206 | + }); |
| 207 | + let earth_type: usize = args[4].parse().unwrap_or_else(|_| { |
| 208 | + eprintln!("エラー: 地格の吉凶が不正です。"); |
| 209 | + process::exit(1); |
| 210 | + }); |
| 211 | + let external_type: usize = args[5].parse().unwrap_or_else(|_| { |
| 212 | + eprintln!("エラー: 外格の吉凶が不正です。"); |
| 213 | + process::exit(1); |
| 214 | + }); |
| 215 | + let total_type: usize = args[6].parse().unwrap_or_else(|_| { |
| 216 | + eprintln!("エラー: 総格の吉凶が不正です。"); |
| 217 | + process::exit(1); |
| 218 | + }); |
| 219 | + let max_count: usize = args[7].parse().unwrap_or_else(|_| { |
| 220 | + eprintln!("エラー: 無効な最大検索数です。"); |
| 221 | + process::exit(1); |
| 222 | + }); |
| 223 | + |
| 224 | + println!( |
| 225 | + "指定された条件に合致する画数の組み合わせを最大 {} 件検索します...", |
| 226 | + max_count |
| 227 | + ); |
| 228 | + |
| 229 | + let mut count = 0; |
| 230 | + for last1 in 1..=30 { |
| 231 | + for last2 in 1..=30 { |
| 232 | + for first1 in 1..=30 { |
| 233 | + for first2 in 1..=30 { |
| 234 | + let last_names = vec![last1, last2]; |
| 235 | + let first_names = vec![first1, first2]; |
| 236 | + let grades = calculate_five_grades(&last_names, &first_names); |
| 237 | + |
| 238 | + let celestial_ok = celestial_type == 0 |
| 239 | + || get_fortune_by_number(grades.celestial) |
| 240 | + == get_fortune_string(&celestial_type); |
| 241 | + let human_ok = human_type == 0 |
| 242 | + || get_fortune_by_number(grades.human) |
| 243 | + == get_fortune_string(&human_type); |
| 244 | + let earth_ok = earth_type == 0 |
| 245 | + || get_fortune_by_number(grades.earth) |
| 246 | + == get_fortune_string(&earth_type); |
| 247 | + let external_ok = external_type == 0 |
| 248 | + || get_fortune_by_number(grades.external) |
| 249 | + == get_fortune_string(&external_type); |
| 250 | + let total_ok = total_type == 0 |
| 251 | + || get_fortune_by_number(grades.total) |
| 252 | + == get_fortune_string(&total_type); |
| 253 | + |
| 254 | + if celestial_ok && human_ok && earth_ok && external_ok && total_ok { |
| 255 | + println!("名字の画数: {:?}, 名前の画数: {:?}, 天格:{} 人格:{} 地格:{} 外格:{} 総格:{}", |
| 256 | + last_names, first_names, |
| 257 | + get_fortune_by_number(grades.celestial), |
| 258 | + get_fortune_by_number(grades.human), |
| 259 | + get_fortune_by_number(grades.earth), |
| 260 | + get_fortune_by_number(grades.external), |
| 261 | + get_fortune_by_number(grades.total) |
| 262 | + ); |
| 263 | + count += 1; |
| 264 | + } |
| 265 | + |
| 266 | + if count >= max_count { |
| 267 | + return; |
| 268 | + } |
| 269 | + } |
| 270 | + } |
| 271 | + } |
| 272 | + } |
| 273 | + println!("検索を終了しました。"); |
| 274 | + } |
| 275 | + _ => { |
| 276 | + eprintln!("エラー: 無効なコマンドです。"); |
| 277 | + print_usage(); |
| 278 | + process::exit(1); |
| 279 | + } |
| 280 | + } |
| 281 | +} |
0 commit comments