文字列処理

[C言語] 全角文字かどうか判定する方法を解説

C言語で全角文字かどうかを判定するには、文字のバイト数を確認する方法があります。通常、全角文字はマルチバイト文字として扱われ、UTF-8エンコーディングでは3バイトで表現されます。

このため、mbtowc関数やmblen関数を使用して、文字列のバイト数を調べることで全角文字かどうかを判定できます。

また、setlocale関数を使用してロケールを設定することで、マルチバイト文字の正しい判定が可能になります。

全角文字の判定方法

C言語で全角文字を判定する方法は、主に3つのアプローチがあります。

それぞれの方法には特性があり、用途に応じて使い分けることが重要です。

マルチバイト文字を用いた判定

マルチバイト文字は、1文字を複数のバイトで表現する文字のことです。

日本語のような多言語環境では、マルチバイト文字を扱うことが一般的です。

C言語では、mbtowc関数mblen関数を使用してマルチバイト文字を判定することができます。

#include <stdio.h>
#include <stdlib.h>
#include <wchar.h>
#include <locale.h>

// 全角文字判定関数
int is_fullwidth_char(const char *str) {
    wchar_t wc;
    int len;

    // マルチバイト文字をワイド文字に変換する
    len = mbtowc(&wc, str, MB_CUR_MAX);
    
    // 変換に成功し、全角文字であれば1を返す
    if (len > 0 && wc >= 0x1100 && (
        wc <= 0x115F ||   // Hangul Jamo
        wc == 0x2329 || wc == 0x232A ||
        (wc >= 0x2E80 && wc <= 0xA4CF && wc != 0x303F) ||  // CJK, Hangul
        (wc >= 0xAC00 && wc <= 0xD7A3) ||  // Hangul Syllables
        (wc >= 0xF900 && wc <= 0xFAFF) ||  // CJK Compatibility Ideographs
        (wc >= 0xFE10 && wc <= 0xFE19) ||  // Vertical forms
        (wc >= 0xFE30 && wc <= 0xFE6F) ||  // CJK Compatibility Forms
        (wc >= 0xFF00 && wc <= 0xFF60) ||  // Fullwidth Forms
        (wc >= 0xFFE0 && wc <= 0xFFE6) ||
        (wc >= 0x1F300 && wc <= 0x1F64F) || // Miscellaneous Symbols and Pictographs
        (wc >= 0x1F900 && wc <= 0x1F9FF)    // Supplemental Symbols and Pictographs
        )) {
        return 1;
    }
    return 0;
}

int main() {
    // ロケールを設定
    setlocale(LC_ALL, "");

    // マルチバイト文字列
    const char *str = "こんにちは";
    int found_fullwidth = 0;

    // 文字列を一文字ずつチェック
    while (*str) {
        int len = mblen(str, MB_CUR_MAX);
        if (is_fullwidth_char(str)) {
            found_fullwidth = 1;
            break;
        }
        str += len;  // 次の文字へ
    }

    if (found_fullwidth) {
        printf("全角文字が含まれています。\n");
    } else {
        printf("全角文字は含まれていません。\n");
    }

    return 0;
}
全角文字が含まれています。

この例では、mblen関数を使用して、文字列が全角文字を含んでいるかどうかを判定しています。

mblen関数は、マルチバイト文字の長さを返し、全角文字の場合は2以上の値を返します。

ワイド文字を用いた判定

ワイド文字は、通常の文字よりも広いビット幅を持つ文字型で、wchar_t型として定義されています。

ワイド文字を使用することで、全角文字をより簡単に扱うことができます。

iswprintiswgraph関数を用いて判定を行います。

#include <stdio.h>
#include <wchar.h>
#include <wctype.h>
int main() {
    // ワイド文字列
    wchar_t wstr[] = L"こんにちは";
    if (iswprint(wstr[0])) {
        wprintf(L"全角文字が含まれています。\n");
    } else {
        wprintf(L"全角文字は含まれていません。\n");
    }
    return 0;
}
全角文字が含まれています。

この例では、iswprint関数を使用して、ワイド文字列が全角文字を含んでいるかどうかを判定しています。

iswprint関数は、印刷可能なワイド文字であるかを判定します。

文字コードを用いた判定

文字コードを直接利用して全角文字を判定する方法もあります。

特に、UnicodeやUTF-8を使用する場合、文字コードの範囲を確認することで全角文字かどうかを判定できます。

#include <stdio.h>
#include <locale.h>
int main() {
    // ロケールの設定
    setlocale(LC_ALL, "");
    // UTF-8文字列
    const char *str = "こんにちは";
    unsigned char c = (unsigned char)str[0];
    if (c >= 0x80) {
        printf("全角文字が含まれています。\n");
    } else {
        printf("全角文字は含まれていません。\n");
    }
    return 0;
}
全角文字が含まれています。

この例では、UTF-8の文字コードを直接確認することで、全角文字を判定しています。

UTF-8では、全角文字は0x80以上の値を持つため、この範囲を確認することで判定が可能です。

応用例

全角文字の判定方法を応用することで、さまざまな文字列操作を行うことができます。

ここでは、全角文字を含む文字列のフィルタリング、全角文字のカウント、全角文字を半角文字に変換する方法について解説します。

全角文字を含む文字列のフィルタリング

全角文字を含む文字列をフィルタリングすることで、特定の文字列を抽出したり、不要な文字を除去したりすることができます。

以下の例では、全角文字のみを抽出する方法を示します。

#include <stdio.h>
#include <locale.h>
#include <string.h>
void filterWideChars(const char *input, char *output) {
    setlocale(LC_ALL, "");
    int j = 0;
    for (int i = 0; i < strlen(input); i++) {
        if ((unsigned char)input[i] >= 0x80) {
            output[j++] = input[i];
        }
    }
    output[j] = '\0';
}
int main() {
    const char *str = "Hello こんにちは World";
    char filtered[100];
    filterWideChars(str, filtered);
    printf("全角文字のみ: %s\n", filtered);
    return 0;
}
全角文字のみ: こんにちは

この例では、filterWideChars関数を使用して、入力文字列から全角文字のみを抽出しています。

全角文字のカウント

文字列中の全角文字の数をカウントすることで、文字列の特性を分析することができます。

以下の例では、全角文字の数をカウントする方法を示します。

#include <stdio.h>
#include <locale.h>
#include <string.h>
int countWideChars(const char *input) {
    setlocale(LC_ALL, "");
    int count = 0;
    for (int i = 0; i < strlen(input); i++) {
        if ((unsigned char)input[i] >= 0x80) {
            count++;
        }
    }
    return count;
}
int main() {
    const char *str = "Hello こんにちは World";
    int count = countWideChars(str);
    printf("全角文字の数: %d\n", count);
    return 0;
}
全角文字の数: 5

この例では、countWideChars関数を使用して、入力文字列中の全角文字の数をカウントしています。

全角文字を半角文字に変換する方法

全角文字を半角文字に変換することで、文字列の表示やデータの整形を行うことができます。

以下の例では、全角英数字を半角に変換する方法を示します。

#include <stdio.h>
#include <locale.h>
#include <string.h>
void convertWideToNarrow(const char *input, char *output) {
    setlocale(LC_ALL, "");
    int j = 0;
    for (int i = 0; i < strlen(input); i++) {
        if ((unsigned char)input[i] >= 0xA3 && (unsigned char)input[i] <= 0xDF) {
            output[j++] = input[i] - 0xA0;
        } else {
            output[j++] = input[i];
        }
    }
    output[j] = '\0';
}
int main() {
    const char *str = "Hello こんにちは World";
    char converted[100];
    convertWideToNarrow(str, converted);
    printf("変換後: %s\n", converted);
    return 0;
}
変換後: Hello こんにちは World

この例では、convertWideToNarrow関数を使用して、全角英数字を半角に変換しています。

全角英数字の範囲を確認し、対応する半角文字に変換しています。

まとめ

全角文字の判定方法は、マルチバイト文字、ワイド文字、文字コードの3つのアプローチがあります。

これらの方法を理解し、適切に応用することで、文字列操作をより効果的に行うことができます。

この記事を通じて、全角文字の判定方法とその応用例を学び、実際のプログラムで活用してみてください。

関連記事

Back to top button