カテゴリー : .NETチップス

 

.NET 整数を切り上げる

C#、VB.NETで整数を切り上げる場合も、「.NET 小数点以下を切り上げる」で作成したRoundUpメソッドが利用できます。
 
        /// <summary>
        /// 値の小数部を切り上げ、指定の桁数に丸めます
        /// </summary>
        /// <param name="value"></param>
        /// <param name="decimals">小数部桁数</param>
        /// <returns>丸められた値</returns>
        private double RoundUp(double value, int decimals)
        {
            // 小数部桁数の10の累乗を取得
            double pow = Math.Pow(10, decimals);

            return 0 <= value ? Math.Ceiling(value * pow) / pow :
                Math.Floor(value * pow) / pow;
        }
 
 
このページでは、上記RoundUpメソッドを実際に動かした時の挙動を確認できます。
 
小数部桁数に「-3」を指定すると100の位を切り上げます。「1400」⇒「2000」という動きになり、ExcelのROUNDUPメソッドと同じ動作をします。もちろん通常通り小数点以下を切り上げることもできます。
 
RoundUp( 
 , 
 ); 
実行結果:
 
 

.NET 整数を切り捨てる

C#、VB.NETで整数を切り捨てる場合も、「.NET 小数点以下を切り捨てる」で作成したTruncateメソッドが利用できます。
 
        /// <summary>
        /// 値の小数部を切り捨て、指定の桁数に丸めます
        /// </summary>
        /// <param name="value"></param>
        /// <param name="decimals">小数部桁数</param>
        /// <returns>丸められた値</returns>
        private double Truncate(double value, int decimals)
        {
            // 小数部桁数の10の累乗を取得
            double pow = Math.Pow(10, decimals);

            return 0 <= value ? Math.Floor(value * pow) / pow :
                Math.Ceiling(value * pow) / pow;
        }
 
 
このページでは、上記Truncateメソッドを実際に動かした時の挙動を確認できます。
 
小数部桁数に「-3」を指定すると100の位を切り捨てます。「1500」⇒「1000」という動きになり、ExcelのROUNDDOWNメソッドと同じ動作をします。もちろん通常通り小数点以下を切り捨てることもできます。
 
Truncate( 
 , 
 ); 
実行結果:
 
 

.NET 整数を四捨五入する

C#、VB.NETで整数を四捨五入する場合は、「Math.Round」メソッドを使ってメソッドを自作する必要があります。
 
        /// <summary>
        /// 値を四捨五入します
        /// </summary>
        /// <param name="value"></param>
        /// <param name="decimals">小数部桁数</param>
        /// <param name="mode">丸める方法</param>
        /// <returns>丸められた値</returns>
        private double Round(double value, int decimals,
            MidpointRounding mode)
        {
            // 小数部桁数の10の累乗を取得
            double pow = Math.Pow(10, decimals);

            return Math.Round(value * pow, mode) / pow;
        }
 
 
このページでは、上記Roundメソッドを実際に動かした時の挙動を確認できます。
 
小数部桁数に「-3」を指定すると100の位を四捨五入します。「1500」⇒「2000」という動きになり、ExcelのRoundメソッドと同じ動作をします。もちろん通常通り小数点以下を四捨五入することもできます。
 
Round( 
 , 
 , 
 ); 
実行結果:
 
 

.NET 小数点以下を切り上げる

C#、VB.NETで小数点以下を切り上げる場合は「Math.Floor」と「Math.Ceiling」メソッドを組み合わせ、用途に合わせてメソッドを自作する必要があります。
 
        /// <summary>
        /// 値の小数部を切り上げ、指定の桁数に丸めます
        /// </summary>
        /// <param name="value"></param>
        /// <param name="decimals">小数部桁数</param>
        /// <returns>丸められた値</returns>
        private double RoundUp(double value, int decimals)
        {
            // 小数部桁数の10の累乗を取得
            double pow = Math.Pow(10, decimals);

            return 0 <= value ? Math.Ceiling(value * pow) / pow :
                Math.Floor(value * pow) / pow;
        }
 
 
上記RoundUpメソッドは、符号を無視して絶対値を切り上げる(常に正負の無限大へ近づく)丸めになります。
 
このページでは、上記RoundUpメソッドを実際に動かした時の挙動を確認できます。
 
値と、小数点以下の桁数を入力し実行ボタンをクリックすると、小数部を指定された桁数に成型した値を実行結果に表示します(小数点第二位までに成型したい場合は小数部桁数へ「2」を指定します)。
 
RoundUp( 
 , 
 ); 
実行結果:
 
 
以下にRoundUpメソッドの挙動をまとめました。「試す」ボタンをクリックすると、書式を入力エリアにコピーしますので、実際の動きを確認することができます。

●書式一覧

内容 書式 結果 試す
100.234を小数点第二位までに成型(小数点第三位を切り上げ) Truncate(100.234, 2); 100.24
-100.234を小数点第二位までに成型(小数点第三位を切り上げ) Truncate(-100.234, 2); -100.24
 

.NET 小数点以下を切り捨てる

C#、VB.NETで小数点以下を切り捨てる場合は、「Math.Floor」と「Math.Ceiling」メソッドを組み合わせ、用途に合わせてメソッドを自作する必要があります。
 
        /// <summary>
        /// 値の小数部を切り捨て、指定の桁数に丸めます
        /// </summary>
        /// <param name="value"></param>
        /// <param name="decimals">小数部桁数</param>
        /// <returns>丸められた値</returns>
        private double Truncate(double value, int decimals)
        {
            // 小数部桁数の10の累乗を取得
            double pow = Math.Pow(10, decimals);

            return 0 <= value ? Math.Floor(value * pow) / pow :
                Math.Ceiling(value * pow) / pow;
        }
 
 
上記Truncateメソッドは、符号を無視して絶対値を切り捨てる(常に0へ近づく)丸めになります。
 
このページでは、上記Truncateメソッドを実際に動かした時の挙動を確認できます。
 
値と、小数点以下の桁数を入力し実行ボタンをクリックすると、小数部を指定された桁数に成型した値を実行結果に表示します(小数点第二位までに成型したい場合は小数部桁数へ「2」を指定します)。
 
Truncate( 
 , 
 ); 
実行結果:
 
 
以下にTruncateメソッドの挙動をまとめました。「試す」ボタンをクリックすると、書式を入力エリアにコピーしますので、実際の動きを確認することができます。

●書式一覧

内容 書式 結果 試す
100.345を小数点第二位までに成型(小数点第三位を切り捨て) Truncate(100.345, 2); 100.34
-100.345を小数点第二位までに成型(小数点第三位を切り捨て) Truncate(-100.345, 2); -100.34
 

.NET 小数点以下を四捨五入する

C#、VB.NETで小数点以下を四捨五入する場合は「Math.Round」メソッドを使いますが、通常の四捨五入と異なる動きをする場合があります。
 
論より証拠。以下の値に「2.5」を入力し実行ボタンをクリックすると、実行結果に「2.0」と表示されます。
 
Math.Round( 
 ); 
実行結果:
 
 
これは「最近接偶数への丸め」や「銀行家の丸め」と呼ばれ、端数が「0.5」のときに結果が偶数になるような丸め方をするためです。
 
なぜこのような複雑な仕様なのでしょうか?
 
通常の四捨五入の場合、切り捨てられる端数が「1、2、3、4」の4個なのに対し、切り上げられる端数が「5、6、7、8、9」の5個と切り上げられる確率のほうが高いため、丸めた値をたくさん足すと誤差が大きくなってしまいます。
 
そこで「0.5」を常に偶数になるように丸めると、「1.5」が「2.0」、「2.5」が「2.0」と切り上げと切り捨てが等しい確率で発生するため、丸めた値をたくさん足した場合も誤差が少なくなるのです。
 
IEEE 754でも定められている通り、浮動小数点数の丸め方としては通常の四捨五入よりも一般的ではあるのですが、私は普通の四捨五入がしたいんです!
 
その場合は「Math.Round」メソッドの引数に「MidpointRounding.AwayFromZero」を指定します。
 
Math.Round( 
 , 
 );
実行結果:
 
 
Math.Round」メソッドの引数に「MidpointRounding.AwayFromZero」を指定すると「2.5」を「3.0」へ四捨五入してくれます。「銀行家の丸め」をしたい場合は「MidpointRounding.ToEven」を指定します。
 
もちろん小数部を指定の桁数で四捨五入することも可能です。
 
Math.Round( 
 , 
 , 
 ); 
実行結果:
 
 

.NET Substringで右から部分文字列を取得する

C#、VB.NETのString.Substringメソッドで、後ろから文字列を切り出すには、部分文字列の開始位置に「文字列の長さ-部分文字列の長さ」を設定します。
 
        /// <summary>
        /// 文字列からの部分文字列の抽出を右から行います
        /// </summary>
        /// <param name="target">対象の文字列</param>
        /// <param name="length">部分文字列の長さ</param>
        /// <returns>文字列の右から抽出された部分文字列</returns>
        public string SubstringRight(string target, int length)
        {
            return target.Substring(target.Length - length, length);
        }
 
 
以下のエリアではSubstringRightメソッドを実際に動かした時の挙動を確認できます。
 
SubstringRight(
 ", 
 );
実行結果:
""
 

.NET 正規表現におけるRegexOptions.Multilineの挙動について

C#、VB.NETで正規表現による検索を行う際、オプションに「Multiline」を指定してもパターンにマッチしない場合があります。
 
たとえばパターンに「@"^\d+$"」を指定して以下の文字列を検索すると、最終行の「789」にしかマッチしません。
 
abc
123
456
789
 
これはパターンの「$」が「改行コード (\n) または入力文字列の末尾と一致する」ように動きますが、「復帰と改行コード(\r\n)の組み合わせとは一致しない」仕様のためです。
 
 
この現象は「$」の代わりに部分式「\r?$」を用いることで回避できます。
 
パターンに「@"^\d+\r?$"」を指定した場合、
 
abc
123
456
789
 
となりますが、これでは改行コードまでマッチしてしまいました。上記例でパターンにマッチした数字のみ必要な場合は、パターンに「@"(^\d+)(\r?$)"」を指定し、マッチした文字列から「$1」にて部分文字列を抽出します。
 
以下はパターンにマッチした数字をシングルコートで囲うサンプルです。
 
        // 数字で始まり数字で終わる行の数字をシングルコートで囲います
        private string AddSingleCoat(string target)
        {
            Regex numberCR = new Regex(@"(^\d+)(\r?$)",
                RegexOptions.Multiline);

            return numberCR.Replace(target, "'$1'$2");
        }
 

.NET 正規表現の動作確認

C#、VB.NETで正規表現による検索を行った時の挙動を確認できます。
 
正規表現のパターンと検索対象を入力し実行ボタンをクリックすると、パターンにマッチした個所を黄色でハイライト表示します。
 
逐語的リテラル文字列「@"~"」を使用しない場合は、\マークをエスケープする必要があります。たとえば数字を検索する場合は「\d」を使用しますが、標準リテラル文字列の場合は「\\d」と指定する必要があります。
 
 
 
 
正規表現パターン:
new Regex(
 ",
    RegexOptions.
);
 
検索対象:

 
※正規表現パターンの改行コード、「\r\n」と「\n」は同一視します。
 

.NET String.IndexOfの動作確認

C#、VB.NETのString.IndexOfメソッドを実際に動かした時の挙動を確認できます。
 
ベースとなる文字列、値と検索の開始位置、文字数などを入力し実行ボタンをクリックすると、値が最初に出現する0から始まるインデックスを実行結果に表示します。
 
 ".IndexOf(" 
 ");
実行結果:
 
 
 ".IndexOf(" 
 ", 
 );
実行結果:
 
 
 ".IndexOf(" 
 ", 
 , 
 );
実行結果:
 
 
以下にString.IndexOfの挙動をまとめました。「試す」ボタンをクリックすると、書式を入力エリアにコピーしますので、実際の動きを確認することができます。

●書式一覧

取得内容 書式 結果 試す
"ABCBA"から"A"のインデックスを取得 "ABCBA".IndexOf("A"); 0
"ABCBA"から"A"のインデックスを取得。検索は"C"の位置から行う "ABCBA".IndexOf("A", 2); 4
"ABCBA"から"A"のインデックスを取得。検索は"C"の位置から3文字分行う "ABCBA".IndexOf("A", 2, 3); 4
"ABCBA"から"A"のインデックスを取得。検索は"C"の位置から2文字分行う "ABCBA".IndexOf("A", 2, 2); -1
g h T
 9,610 Total Views