Namespaces
Variants

std::basic_string<CharT,Traits,Allocator>:: compare

From cppreference.net
std::basic_string
int compare ( const basic_string & str ) const ;
(1) (C++11以降noexcept)
(C++20以降constexpr)
int compare ( size_type pos1, size_type count1,
const basic_string & str ) const ;
(2) (C++20以降constexpr)
(3)
int compare ( size_type pos1, size_type count1,

const basic_string & str,

size_type pos2, size_type count2 ) const ;
(C++14まで)
int compare ( size_type pos1, size_type count1,

const basic_string & str,

size_type pos2, size_type count2 = npos ) const ;
(C++14以降)
(C++20以降constexpr)
int compare ( const CharT * s ) const ;
(4) (C++20以降constexpr)
int compare ( size_type pos1, size_type count1,
const CharT * s ) const ;
(5) (C++20以降constexpr)
int compare ( size_type pos1, size_type count1,
const CharT * s, size_type count2 ) const ;
(6) (C++20以降constexpr)
template < class StringViewLike >
int compare ( const StringViewLike & t ) const noexcept ( /* 下記参照 */ ) ;
(7) (C++17以降)
(C++20以降constexpr)
template < class StringViewLike >

int compare ( size_type pos1, size_type count1,

const StringViewLike & t ) const ;
(8) (C++17以降)
(C++20以降constexpr)
template < class StringViewLike >

int compare ( size_type pos1, size_type count1,
const StringViewLike & t,

size_type pos2, size_type count2 = npos ) const ;
(9) (C++17以降)
(C++20以降constexpr)

2つの文字シーケンスを比較します。

1) この文字列を str と比較します。
2) この文字列の [ pos1 , pos1 + count1 ) 部分文字列を str と比較する。
  • count1 > size ( ) - pos1 の場合、部分文字列は [ pos1 , size ( ) ) となる。
3) この文字列の [ pos1 , pos1 + count1 ) 部分文字列と、 [ pos2 , pos2 + count2 ) 部分文字列を比較する。
  • count1 > size ( ) - pos1 の場合、最初の部分文字列は [ pos1 , size ( ) ) となる。
  • count2 > str. size ( ) - pos2 の場合、2番目の部分文字列は [ pos2 , str. size ( ) ) となる。
4) この文字列を、 s が指す文字から始まる長さ Traits :: length ( s ) のNULL終端文字シーケンスと比較します。
5) この文字列の [ pos1 , pos1 + count1 ) 部分文字列を、 s が指す文字から始まるnull終端文字シーケンスと比較します。比較長さは Traits :: length ( s ) です。
  • count1 > size ( ) - pos1 の場合、部分文字列は [ pos1 , size ( ) ) となります。
6) この文字列の [ pos1 , pos1 + count1 ) 部分文字列を、範囲 [ s , s + count2 ) 内の文字と比較します。 [ s , s + count2 ) の文字にはnull文字が含まれる可能性があります。
  • count1 > size ( ) - pos1 の場合、部分文字列は [ pos1 , size ( ) ) となります。
7-9) t を文字列ビュー sv に暗黙的に変換する( std:: basic_string_view < CharT, Traits > sv = t ; によって行われるかのように)、その後
7) この文字列を sv と比較する;
8) この文字列の [ pos1 , pos1 + count1 ) 部分文字列を sv と比較する。動作は std:: basic_string_view < CharT, Traits > ( * this ) . substr ( pos1, count1 ) . compare ( sv ) を呼び出した場合と同様。
9) この文字列の [ pos1 , pos1 + count1 ) 部分文字列を、 [ pos2 , pos2 + count2 ) の部分文字列と比較する。比較は std:: basic_string_view < CharT, Traits > ( * this )
. substr ( pos1, count1 ) . compare ( sv. substr ( pos2, count2 ) )
によって行われるかのようである。
これらのオーバーロードは、以下の条件が満たされる場合にのみオーバーロード解決に参加します: std:: is_convertible_v < const StringViewLike & ,
std:: basic_string_view < CharT, Traits >>
true であり、かつ std:: is_convertible_v < const StringViewLike & , const CharT * > false である場合。

count1 文字からなる文字シーケンス( data1 から開始)が、 count2 文字からなる文字シーケンス( data2 から開始)と次のように比較されます:

  • まず、比較する文字数を計算します。計算方法は size_type rlen = std:: min ( count1, count2 ) のように行います。
  • 次に、シーケンスを比較するために Traits :: compare ( data1, data2, rlen ) を呼び出します。標準文字列の場合、この関数は文字単位の辞書順比較を実行します。結果がゼロ(これまでの文字シーケンスが等しい)の場合、それらのサイズは以下のように比較されます:
条件 結果 戻り値
Traits::compare( data1 , data2 , rlen ) < 0 data1 data2 より 小さい < 0
Traits::compare( data1 , data2 , rlen ) == 0 size1 < size2 data1 data2 より 小さい < 0
size1 == size2 data1 data2 等しい 0
size1 > size2 data1 data2 より 大きい > 0
Traits::compare( data1 , data2 , rlen ) > 0 data1 data2 より 大きい > 0

目次

パラメータ

str - 比較対象の他の文字列
s - 比較対象の文字列へのポインタ
count1 - 比較するこの文字列の文字数
pos1 - 比較するこの文字列の最初の文字の位置
count2 - 比較する指定された文字列の文字数
pos2 - 比較する指定された文字列の最初の文字の位置
t - 比較対象のオブジェクト( std::basic_string_view に変換可能)

戻り値

  • 引数で指定された文字シーケンスより、辞書順で * this が前に現れる場合は負の値。
  • 両方の文字シーケンスが等価な場合はゼロ。
  • 引数で指定された文字シーケンスより、辞書順で * this が後に現れる場合は正の値。

例外

pos1 または pos2 という名前のパラメータを受け取るオーバーロードは、 引数が範囲外の場合 std::out_of_range をスローします。

7)
noexcept 指定:
noexcept ( std:: is_nothrow_convertible_v < const T & , std:: basic_string_view < CharT, Traits >> )
8,9) std::basic_string_view への変換でスローされたあらゆる例外をスローする。

何らかの理由で例外がスローされた場合、この関数は何も効果を持ちません( strong exception safety guarantee )。

実装例

オーバーロード (1)
template<class CharT, class Traits, class Alloc>
int std::basic_string<CharT, Traits, Alloc>::compare
    (const std::basic_string& s) const noexcept
{
    size_type lhs_sz = size();
    size_type rhs_sz = s.size();
    int result = traits_type::compare(data(), s.data(), std::min(lhs_sz, rhs_sz));
    if (result != 0)
        return result;
    if (lhs_sz < rhs_sz)
        return -1;
    if (lhs_sz > rhs_sz)
        return 1;
    return 0;
}

注記

三方比較が不要な状況では、 std::basic_string は通常の 関係演算子 ( < , <= , == , > , など) を提供します。

デフォルトでは(デフォルトの std::char_traits を使用した場合)、この関数はロケール依存ではありません。ロケールを考慮した三方文字列比較については、 std::collate::compare を参照してください。

#include <cassert>
#include <iomanip>
#include <iostream>
#include <string>
#include <string_view>
void print_compare_result(std::string_view str1,
                          std::string_view str2,
                          int compare_result)
{
    if (compare_result < 0)
        std::cout << std::quoted(str1) << " comes before "
                  << std::quoted(str2) << ".\n";
    else if (compare_result > 0)
        std::cout << std::quoted(str2) << " comes before "
                  << std::quoted(str1) << ".\n";
    else
        std::cout << std::quoted(str1) << " and "
                  << std::quoted(str2) << " are the same.\n";
}
int main()
{
    std::string batman{"Batman"};
    std::string superman{"Superman"};
    int compare_result{0};
    // 1) 他の文字列と比較
    compare_result = batman.compare(superman);
    std::cout << "1) ";
    print_compare_result("Batman", "Superman", compare_result);
    // 2) 部分文字列を他の文字列と比較
    compare_result = batman.compare(3, 3, superman);
    std::cout << "2) ";
    print_compare_result("man", "Superman", compare_result);
    // 3) 部分文字列を他の部分文字列と比較
    compare_result = batman.compare(3, 3, superman, 5, 3);
    std::cout << "3) ";
    print_compare_result("man", "man", compare_result);
    // 部分文字列を他の部分文字列と比較
    // 他の文字列の末尾をデフォルトとして使用
    assert(compare_result == batman.compare(3, 3, superman, 5));
    // 4) 文字ポインタと比較
    compare_result = batman.compare("Superman");
    std::cout << "4) ";
    print_compare_result("Batman", "Superman", compare_result);
    // 5) 部分文字列を文字ポインタと比較
    compare_result = batman.compare(3, 3, "Superman");
    std::cout << "5) ";
    print_compare_result("man", "Superman", compare_result);
    // 6) 部分文字列を文字ポインタの部分文字列と比較
    compare_result = batman.compare(0, 3, "Superman", 5);
    std::cout << "6) ";
    print_compare_result("Bat", "Super", compare_result);
}

出力:

1) "Batman" comes before "Superman".
2) "Superman" comes before "man".
3) "man" and "man" are the same.
4) "Batman" comes before "Superman".
5) "Superman" comes before "man".
6) "Bat" comes before "Super".

不具合報告

以下の動作変更の欠陥報告書は、以前に公開されたC++規格に対して遡及的に適用されました。

DR 適用対象 公開時の動作 修正後の動作
LWG 5 C++98 オーバーロード (6) のパラメータ count2 npos のデフォルト引数があった デフォルト引数を削除し、
オーバーロード (5) (6) に分割
LWG 847 C++98 例外安全性の保証がなかった 強い例外安全性保証を追加
LWG 2946 C++17 オーバーロード (7) が一部の場合で曖昧性を引き起こした テンプレート化することで回避
P1148R0 C++17 オーバーロード (7) の noexcept が LWG2946 の解決により
誤って削除された
復元

関連項目

(C++20で削除) (C++20で削除) (C++20で削除) (C++20で削除) (C++20で削除) (C++20)
2つの文字列を辞書順で比較する
(関数テンプレート)
部分文字列を返す
(公開メンバ関数)
文字列の辞書順比較とハッシュを定義する
(クラステンプレート)
現在のロケールに従って2つの文字列を比較する
(関数)
一方の範囲が他方よりも辞書順で小さい場合に true を返す
(関数テンプレート)
2つのビューを比較する
( std::basic_string_view<CharT,Traits> の公開メンバ関数)