paiza レベルアップ問題集 「STEP: 7 N が M ずつ増えたときにいつ K を越える?」をPythonとGASで解いてみた

この記事を読むことで、PythonとGASでwhileループを使って加算をしていく過程で、変数がどのように変化するのかを学べます。
整数NにMずつ加算して行って、何回加算したらKを超えるかを求めます。

このコーナーでは、学習コンテンツpaizaラーニングレベルアップ問題集をPythonとGASの両方で解いて全コードの解説をしています。
PythonとGASの両方のコードを用いて、全コード及び部分的にも可能な限り詳細に記載いたしました。

GASはスプレッドシートを使っています。
GASはGoogle Apps Scriptと言って、JavaScriptの文法をベースにしているので、JavaScriptの学習中の方にもお役立て出来るかも知れません。

サイトマップはこちらから

paizaレベルアップ問題集でPythonとGASを解いて見たに戻る
メインメニューに戻る
Python自作サンプル
GASサンプル
基本情報技術者試験

paizaでの解答はPythonで行いましたが、この記事ではPythonのコードと共に、同じ問題を現在学習中のGASだったらどう解くのか、スプレッドシートでバインドして作ってみました。

N が M ずつ増えたときにいつ K を越える? (paizaランク D 相当)

問題:
整数 N, M, K が与えられます。
N が M ずつ増えるとき、何回目に K を越えるか出力してください。

この記事では、下記の入力例3の場合を例にして、N=1がM=3ずつ増えると「いつK=8を超えるか」を求めて行きます。

入力例3
1 3 8

出力例3
3

ではまず、Pythonで解いてみます。

今回は、paiza.ioを使って解きます。paiza.ioの使い方はこちらから。

■ Pythonでの解き方 ■

下準備として、paiza.ioにこの様に入力します。
(入力例1をそのままioにコピーしただけ。)

手順として、

1:N,M,Kを標準入力で取り込む

2:ループの何回目の足し算でNがKを超えるかを数える変数countを0で初期化する


3:whileループでN<=Kの条件を満たす間、ループを回して加算する。countをインクリメントする

4:countを表示

で、行います。

まずは、プログラムの各変数の動きを追いやすいように、トレースのio出力結果と、トレースのコードを添えます。

Whileループのトレースをします。

1回目の加算

2回目の除算

3回目の除算

ここまでのwhileループによるトレースの部分のコードです。

#N,M,Kを標準入力で取り込む
N,M,K=map(int,input().rstrip().split(' '))

#ループの何回目の足し算でNがKを超えるかを数える変数countを0で初期化する
count=0


#whileループでN<=Kの条件を満たす間、ループを回して加算する。countをインクリメントする。

print('<<<ループに入る>>>')

while N<=K:
    print('計算前のNの値:「'+str(N)+'」')
    print(str(N)+'に'+str(M)+'を加算\n')
    #ここで、NにMを加算する
    N+=M
    print('計算後のNの値:「'+str(N)+'」')
    if N<=K:
        print('K:'+str(K)+'まで'+str(K-N)+'足りない')
    else:
        print('K:'+str(K)+'に対してN:'+str(N)+'で、Kを超えた!!')
    count+=1
    print('加算回数【'+str(count)+'】回')
    print('-----------------------')


print('<<<ループを抜けた>>>')

#countを表示
print(count)

このままでは、出力結果である出力例3に対して冗長なコードが含まれているので、解答以外のprint文をコメントアウトします。

#N,M,Kを標準入力で取り込む
N,M,K=map(int,input().rstrip().split(' '))

#ループの何回目の足し算でNがKを超えるかを数える変数countを0で初期化する
count=0


#whileループでN<=Kの条件を満たす間、ループを回して加算する。countをインクリメントする。

#print('<<<ループに入る>>>')

while N<=K:
    #print('計算前のNの値:「'+str(N)+'」')
    #print(str(N)+'に'+str(M)+'を加算\n')
    #ここで、NにMを加算する
    N+=M
    #print('計算後のNの値:「'+str(N)+'」')
    #if N<=K:
        #print('K:'+str(K)+'まで'+str(K-N)+'足りない')
    #else:
        #print('K:'+str(K)+'に対してN:'+str(N)+'で、Kを超えた!!')
    count+=1
    #print('加算回数【'+str(count)+'】回')
    #print('-----------------------')


#print('<<<ループを抜けた>>>')

#countを表示
print(count)

スッキリするように、コメントアウトした部分を省いたコードです。

#N,M,Kを標準入力で取り込む
N,M,K=map(int,input().rstrip().split(' '))


#ループの何回目の足し算でNがKを超えるかを数える変数countを0で初期化する。countをインクリメントする。
count=0


#whileループでN<=Kの条件を満たす間、ループを回して加算する
while N<=K:
    
    #ここで、NにMを加算する
    N+=M
    count+=1
    
#countを表示
print(count)

ioの出力結果です。

■ GASでの解き方 ■

では、同じ問題をGASで解いてみます。
まず、スプレッドシートにこの様に配置しました。

「加算される整数N(=緑のセル「1」)、増加する数M(=灰色のセル「3」)、加算して超える基準値K(=ピンクのセル「8」)」でKを超えるまでに加算した回数をスプレッドシートの黄色いセルの所に出力します。

Whileループで加算する回数を変数countに格納します。
また、countを二次元配列count2に追加して、スプレッドシートに出力します。

※スプレッドシートに表示する場合は、ループを使って一次元配列ではなく、二次元配列としてからの配列に追加をして作成します※

手順はこのようになります。

1:スプレッドシートからアクティブシートをアクセスする

2:整数N,M,Kを取得する配列arrayを宣言する


3:スプレッドシートの緑色のセルにある整数N(この例では「1」)と、灰色のセルにある、加算していく整数M(この例では「3」)と、ピンク色のセルにある加算によって超える基準値の整数K(この例では「8」)を3行1列の配列arrayに取得する


4:arrayを出力して、各数が配列に格納されていることをログで確認する


5:N=array[0][0]、M=array[1][0]、K=array[2][0]として代入する。この時Nのみ変数で、M,Kは定数になる。


6:それぞれの変数、定数が正しく代入されたことをログで確認する


7:NにMを足していく回数countを0で初期化する


8:whileループを使ってNにMずつ加算する(N+=Mを計算)して、countをインクリメントする


9:countを表示する


10:スプレッドシートにcountに格納された加算回数を二次元配列として格納するcount2を宣言する


11:count2に二次元配列としてcountを追加


12:スプレッドシートに出力前のcount2を出力して確認する


13:スプレッドシートの黄色い所に加算回数を二次元配列として格納したcount2を出力する

手順1: スプレッドシートからアクティブシートをアクセスする

const ss=SpreadsheetApp.getActiveSheet();

ここで定数ssにSpreadsheetAppから階層を辿ってアクティブシートにアクセスしています。

手順2:整数N,M,Kを取得する配列arrayを宣言する

let array=[];

手順3:スプレッドシートの緑色のセルにある整数N(この例では「1」)と、灰色のセルにある、加算していく整数M(この例では「3」)と、ピンク色のセルにある加算によって超える基準値の整数K(この例では「8」)を3行1列の配列arrayに取得する

スプレッドシートのセルB1は1行目の2列目なので(1,2)と書き、そこから3行取得するので、引数に3も加えます。

array=ss.getRange(1,2,3).getValues();

手順4:arrayを出力して、各数が配列に格納されていることを確認する

console.log(array);

手順5:N=array[0][0]、M=array[1][0]、K=array[2][0]として代入する。この時Nのみ変数で、M,Kは定数になる。

let N=array[0][0];
const M=array[1][0];
const K=array[2][0];

※ NはMを加えていくので値が変わるから変数、それに対してMや基準値のKは値が変わらないので定数 ※

手順6:各変数・定数が格納されたことを確認する

数値と文字を一緒に出力するときは、[Shiftキー]を押しながら「@」を押して「 ` 」で囲います。

console.log(`N:${N},M:${M},K:${K}`);

手順7:NにMを足していく回数countを0で初期化する

let count=0;

手順8:whileループを使ってNにMずつ加算する(N+=Mを計算)して、countをインクリメントする

1回目の加算

2回目の加算

3回目の加算

Whileループの部分のコードです。

  //whileループを使って余りを配列に格納する
  console.log('<<<whileループに入りました>>>');


  while (N >= 1) {
    console.log(`計算前のNの値:${N}`);
    console.log(`計算前の配列array:[${array}]`);
    console.log(`配列に追加する余り【${N % M}】`);

    //配列に追加
    array.push(N % M);

    //割り算の実行
    N /= M;

    //Nを整数にする
    N = Math.floor(N);

    console.log(`計算後のNの値:${N}`);
    console.log(`計算後の配列array:[${array}]`);

    console.log('------------------------');
  }

  console.log('<<<whileループを抜けました。>>>');

手順9:加算回数countを表示

console.log(count);

手順10:スプレッドシートにcountに格納された加算回数を二次元配列として格納するcount2を宣言する

let count2=[];

手順11:count2に二次元配列としてcountを追加

count2.push([count]);

手順12:スプレッドシートに出力前のcount2を出力して確認する

console.log(count2);

手順13:スプレッドシートの黄色い所に加算回数を二次元配列として格納したcount2を出力する

ss.getRange(6,2).setValue(count2);

実行後のスプレッドシートです。

GASでの全コードはこちらになります。

function loop2no12() {

  //スプレッドシートからアクティブシートをアクセスする
  const ss = SpreadsheetApp.getActiveSheet();

  //整数N,M,Kを取得する配列arrayを宣言する
  let array = [];

  //スプレッドシートの緑色のセルにある整数N(この例では「1」)と、灰色のセルにある、加算していく整数M(この例では「3」)と、ピンク色のセルにある加算によって超える基準値の整数K(この例では「8」)を3行1列の配列arrayに取得する
  array = ss.getRange(1, 2, 3).getValues();

  //arrayを出力して、各数が配列に格納されていることを確認する
  console.log(array);

  //N=array[0][0]、M=array[1][0]、K=array[2][0]として代入する。この時Nのみ変数で、M,Kは定数になる。
  let N = array[0][0];
  const M = array[1][0];
  const K = array[2][0];

  //各変数・定数が格納されたことを確認する
  console.log(`N:${N},M:${M},K:${K}`);

  //NにMを足していく回数countを0で初期化する
  let count = 0;

  //whileループを使ってNにMずつ加算する(N+=Mを計算)して、countをインクリメントする

  console.log('<<<whileループに入る>>>');

  while (N <= K) {
    console.log(`加算前のN:「${N}」`);
    console.log(`NにM=${M}を加算\n`);

    //加算処理とcountのインクリメント
    N += M;
    count++;

    console.log(`加算後のN:「${N}」`);
    console.log(`加算回数【${count}】回`);

    if (N <= K) {
      console.log(`N=${N}はK=${K}まで「${K - N}」足りない`);
    } else {
      console.log(`N=${N}はK=${K}を超えた!!`);
    }

    console.log('-------------------------');

  }

  console.log('<<<whileループを抜けた>>>');

  //countを表示する
  console.log(count);

  //スプレッドシートにcountに格納された加算回数を二次元配列として格納するcount2を宣言する
  let count2 = [];

  //count2に二次元配列としてcountを追加
  count2.push([count]);

  //スプレッドシートに出力前のcount2を出力して確認する
  console.log(count2);

  //スプレッドシートの黄色い所に加算回数を二次元配列として格納したcount2を出力する
  ss.getRange(6, 2).setValue(count2);

}

宜しかったらコピペしてアレンジして見て下さい。
お疲れ様でした、ブレイクタイムフォトはこちらになります。

横浜ランドマークタワーからの絶景!!
大観覧車の赤と青の自然な感じのコントラストに中央が黄金色なのも、また素敵!!

■ 参考文献の紹介■

じっくり丁寧にPythonを学びたい方向け。
まずはpaizaラーニングなどの学習コンテンツで学んで、基礎をマスターしたら、この本でじっくりと初級から中級レベルを目指せます。

初めてGASを学ぶ方向け。
スプレッドシートの基本的な使い方からGASのベースとなるJavaScriptの基礎文法、GASでの初歩的なプログラミングを学べます。

GASに少し慣れて来たら、基礎固めとリファレンスとしてこの本でじっくり学べます。

サイトマップはこちらから

paizaレベルアップ問題集でPythonとGASを解いて見たに戻る
メインメニューに戻る
Python自作サンプル
GASサンプル
基本情報技術者試験

←前の問題へ          次の問題へ→