C++で数値と「+」「-」演算子のみを含む配列式を評価する方法
この記事では、n個の文字列要素からなる配列 arr[] で表現された数式を評価する方法を解説します。配列の各要素は、数値、または演算子「+」「-」のいずれかであり、これらを順に処理して最終的な計算結果を求めるのが課題です。
問題の概要
与えられる式には、数値・「+」記号・「-」記号のみが含まれます。括弧や乗除算は考慮せず、左から順に加減算を適用していきます。
入力例
arr = {"5", "+", "2", "-", "8", "+", "9"}
出力例
8
解説
この式は 5 + 2 - 8 + 9 = 8 として評価されます。
解法アプローチ
解き方はシンプルです。配列を先頭から順に走査し、各演算子に応じて加算または減算を実行します。その際、文字列形式の数値は stoi() 関数を使って整数値へ変換する必要があります。数値と演算子が交互に並んでいるため、インデックスを2つずつ進めることで効率的に処理できます。
C++での実装例
#include <bits/stdc++.h>
using namespace std;
int solveExp(string arr[], int n) {
// 配列が空の場合は0を返す
if (n == 0)
return 0;
int result = stoi(arr[0]); // 先頭の数値を初期値とする
// 数値と演算子が交互に並ぶため、2つずつ進める
for (int i = 2; i < n; i += 2) {
int value = stoi(arr[i]);
if (arr[i - 1] == "+")
result += value;
else
result -= value;
}
return result;
}
int main() {
string arr[] = { "5", "-", "3", "+", "8", "-", "1" };
int n = sizeof(arr) / sizeof(arr[0]);
cout << "計算結果: " << solveExp(arr, n);
return 0;
}実行結果
計算結果: 9
コードの解説
まず先頭の数値を stoi() で整数に変換し、結果の初期値とします。その後、インデックスを2つずつ進めながらループを回します。これは「数値 → 演算子 → 数値」という構造が繰り返されるためです。各ステップでは、直前の演算子が「+」なら加算を、「-」なら減算を行います。
なお、stoi() は符号付きの文字列(例:「-8」)も正しく処理できるため、負の数が1つのトークンとして含まれる場合にも対応可能です。このアルゴリズムの時間計算量は O(n)、空間計算量は O(1) と非常に効率的です。
-
【C++】-1と+1からなる配列に、合計が0となるサイズKの部分集合が存在するか判定する方法
この問題では、1と-1のみから構成される配列 arr[] と整数値 k が与えられます。私たちのタスクは、-1と+1からなる配列の中に、合計が0となるサイズKの部分集合が存在するかどうかを判定することです。問題例で理解しよう入力: arr[] = {-1, 1, -1, -1, 1, 1, -1}, k = 4出力: YES説明:サイズ4の部分集合 {-1, 1, -1, 1} を選ぶと、合計 = -1 + 1 - 1 + 1 = 0 となります。解法の考え方まず、合計が0になるサイズKの部分集合が存在するかどうかを確認する必要があります。部分集合には配列の任意の要素を選べるため、部分集合内に
-
C++で学ぶ式ツリー(Expression Tree)の基本と具体例
式ツリーとは何か式ツリー(Expression Tree)とは、二分木の一種であり、木の各ノードが「演算子」または「オペランド(被演算子)」のいずれかで構成される特殊なデータ構造です。数式を木構造として表現することで、コンパイラや電卓アプリなどが数式を効率的に解析・評価できるようになります。ノードの役割式ツリーにおける各ノードは、次のように役割が分かれています。葉ノード(リーフノード):オペランド(数値や変数)を表します。非葉ノード(内部ノード):演算子(+、-、*、/ など)を表します。つまり、計算の対象となる値は必ず葉に配置され、それらをどのように処理するかを示す演算子が親ノードとして上に