web-dev-qa-db-ja.com

タイプ「int」を「short」に暗黙的に変換できません

フィボナッチ数列を出力するために、次の小さなプログラムを作成しました。

static void Main(string[] args)
{
    Console.Write("Please give a value for n:");
    Int16 n = Int16.Parse(Console.ReadLine());

    Int16 firstNo = 0;
    Int16 secondNo = 1;

    Console.WriteLine(firstNo);
    Console.WriteLine(secondNo);

    for (Int16 i = 0; i < n; i++)
    {
        //Problem on this line                    
        Int16 answer = firstNo + secondNo;

        Console.WriteLine(answer);

        firstNo = secondNo;
        secondNo = answer;
    }

    Console.ReadLine();

}

コンパイルメッセージは次のとおりです。

型 'int'を 'short'に暗黙的に変換することはできません。明示的な変換が存在します(キャストを見逃していますか?)

関連するものはすべてInt16(short)であるため、暗黙の変換が行われているのはなぜですか?そして、より具体的には、なぜここで失敗するのですか(変数に最初にintを割り当てるときではありません)?

説明をいただければ幸いです。

38
m.edmondson

MicrosoftはInt16変数からInt32追加機能を実行するとき。

以下を変更します。

Int16 answer = firstNo + secondNo;

に...

Int16 answer = (Int16)(firstNo + secondNo);
79
m-y
8
abhilash

問題は、2つのInt16を追加すると、他の人が既に指摘したようにInt32になるということです。
2番目の質問、これらの2つの変数の宣言でこの問題が発生しない理由については、こちらで説明します。 http://msdn.Microsoft.com/en-us/library/ybs77ex4% 28v = VS.71%29.aspx

short x = 32767;

上記の宣言では、整数リテラル32767は暗黙的にintからshortに変換されます。整数リテラルが短い保存場所に収まらない場合、コンパイルエラーが発生します。

したがって、宣言で機能する理由は、提供されたリテラルがshortに収まることがわかっているからです。

3
Daniel Hilgarth

何らかの奇妙な理由で、+ =演算子を使用してショートを追加できます。

short answer = 0;
short firstNo = 1;
short secondNo = 2;

answer += firstNo;
answer += secondNo;
2
Karl Gjertsen

プラス演算子は、まずオペランドをintに変換してから加算を行います。結果はintです。 「長い」型から「短い」型への変換は明示的に行われるため、暗黙的にキャストして誤ってデータを失うことはないため、明示的にshortにキャストする必要があります。

なぜint16がintにキャストされるのかという答えは、これが C#spec で定義されているからです。 C#がこのようになっているのは、CLRが動作する方法に密接に一致するように設計されており、CLRには16ビットではなく32/64ビットの算術演算しかないためです。 CLRの他の言語では、これを異なる方法で公開することを選択する場合があります。

2
Andrew Savinykh

この線

 Int16 answer = firstNo + secondNo;

と解釈されます

 Int16 answer = (Int32) (firstNo + secondNo);

Int16算術演算などは存在しないためです。

簡単な解決策:Do Int16を使用しない。 Int32または単にintを使用します。

intはデフォルトの整数型です。 shortとlongは、特別な場合にのみ使用されます。

1
Henk Holterman

2つのInt16変数を合計した結果はInt32です:

Int16 i1 = 1;
Int16 i2 = 2;
var result = i1 + i2;
Console.WriteLine(result.GetType().Name);

Int32を出力します。

1
Aliostad

これは、2つのInt16を追加した結果がInt32であるためです。ここで「変換」の段落を確認してください。 http://msdn.Microsoft.com/en-us/library/ybs77ex4%28v=vs.71%29.aspx

0
Paolo Tedesco