LoginSignup
0
0

C言語 で (3,5,7の倍数) Fizzbuzz 問題 3パターン

Last updated at Posted at 2023-06-30

Fizzbuzz の定番は, 3n, 5n の2種類だが、今回は 7nを追加して3種類にした。以下のコードは、仮に素数が 100種類だったとしても大して長くならないだろう。

Fizzbuzz問題

以下の Fizzbuzz 問題の C/C++ プログラムを書け。

  1. 数値1から 200 までインクリメント出力する。ただし 下記2. の条件を満たす場合はインクリメント数値ではなく下記2.を出力する。

  2. 素数 3, 5, 7 についてそれぞれの倍数である場合は 「(素数) n」と出力する。ただしこれら素数の最小公倍数である場合はそちらを優先し「(最小公倍数) n」と出力する。(e.g.参照)

e.g. 210 なら 105n, 70 なら 35n, 63 なら 021n, 14 なら 07n, 30 なら 015n, 10 なら 005n, 6 なら 003n

ビット演算を使う方法

ビット演算を使う方法
#include <iostream>
using namespace std;
int main(void){
   
     char *name[] = { "(reserved)" , "3n" , "5n", "15n", "7n", "21n", "35n", "105n"};
     int idx;

     for (int n = 1; n <= 200; n++) {
     idx= 7*(n !=0) & 4*(n%7 == 0) + 2*(n%5 == 0)+ 1* (n%3 == 0);  //入力数字の条件分岐に相当する処理
     idx==0 ? cout<< n : cout << name[idx]; cout << endl;
      }
    
}

ビット演算を用いると Fizz-Buzz の条件分岐は ほとんど 1行で済む。条件ごとに 2^n のマスクを取ること。

これは Cじゃなくても同じように書ける。

別解1:三項演算子とポインタ

別解1:三項演算子とポインタ
#include <stdio.h>
int main(){
char *str="105n\n\0 35n\n\0 21n\n\0 15n\n\0 7n\n\0 5n\n\0 3n\n\0 %d\n\0";    

for(int i=0;++i<=200;){
printf(str+(i%105?i%35?i%21?i%15?i%7?i%5?i%3?40:35:30:25:19:13:7:0),i);
}

}

これは printf 関数の仕様に、フォーマット指定子があることとそれが char* であることを利用した、ポインタ演算に依る。

char* str は定義せず、printf に直接書いてもよい。

補遺:多次元配列を用いた書き方

#include <iostream>
using namespace std;
int main(void){   
   char idx;
     for (int n = 1; n <= 200; n++) {
         idx= (char[2][2][2]){'-', 'B', 'C', 'D','E', 'F', 'G', 'H'}[n%7 == 0][n%5 == 0][n%3 == 0];        
     (idx =='-' || n ==0)  ? cout<< n : cout << idx; cout << endl;  
     }   
}

これは題意には沿わない

元記事

0
0
5

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0