質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.35%
Java

Javaは、1995年にサン・マイクロシステムズが開発したプログラミング言語です。表記法はC言語に似ていますが、既存のプログラミング言語の短所を踏まえていちから設計されており、最初からオブジェクト指向性を備えてデザインされています。セキュリティ面が強力であることや、ネットワーク環境での利用に向いていることが特徴です。Javaで作られたソフトウェアは基本的にいかなるプラットフォームでも作動します。

Q&A

解決済

3回答

1821閲覧

long型の数値には末尾にLを付与するがbyte,short型には付与しないのはなぜか

Monkuma

総合スコア3

Java

Javaは、1995年にサン・マイクロシステムズが開発したプログラミング言語です。表記法はC言語に似ていますが、既存のプログラミング言語の短所を踏まえていちから設計されており、最初からオブジェクト指向性を備えてデザインされています。セキュリティ面が強力であることや、ネットワーク環境での利用に向いていることが特徴です。Javaで作られたソフトウェアは基本的にいかなるプラットフォームでも作動します。

1グッド

0クリップ

投稿2021/06/04 12:52

編集2021/06/05 01:49

long型の数値には末尾にl,Lを付与しなければいけません。

なぜなら、数値データのデフォルト型がintであるため。

と認識しています。

しかし、byte,short型のデータを宣言する場合は末尾にb,sを付けなくてもエラーにはなりません。(int型のデータをbyte,short型の変数に代入しようとしているのに)

Java

1short s = 1; 2byte b = 1; 3//コンパイルOK

なぜでしょうか。

よろしくお願いいたします。

追記 2021/06/05
回答をいただいての追記です。
まず、私の質問内容で不正確な箇所があったため以下のとおり修正します。

  • 修正前

long型の数値には末尾にl,Lを付与しなければいけません。

  • 修正後

intサイズを超えるlongの値を扱う場合はl,Lを付与しなければいけません。

irithyllさん
kainaさん
neko_the_shadowさん
ご回答ありがとうございました。

私の質問の仕方が悪く意図が伝わってなかったこと反省しています。。。

Java学習サイトや本などで、

数値リテラルのデフォルト型はintであるためlong型に代入する場合はl,Lを付与しましょう。

との記載が多くみられました。

デフォルト型がintであればbyte,short型にそのまま代入できないことになる。

したがって、矛盾してないか、私の認識不足かまたは別の仕様があるのかと思ったのが今回の質問の背景です。

neko_the_shadowさんの回答が意図に沿ったものだったのでベストアンサーとさせていただきます(他のお2人、申し訳ございません)

以下、ざっくりとまとめておきます。

自動で基本型縮小変換が行われる条件がある。

  1. 代入先の型がbyte,short,charである。
  2. 右辺の値が代入先の型で表現できる。
  3. 右辺は必ず定数式

Java

1short s = 5; 2//コンパイルOK

Java

1short s = 5; 2byte b = s; 3//コンパイルNG

ちなみに浮動種数点型では自動基本型縮小変換は行われないので注意すること。

視点を変えて、lはあるのにs,bがないのはなぜかはirithyllさん、kainaさんに回答していただいた通り。(仕様の背景がよく理解できました!)

回答していただいた方々、本当にありがとうございました!

kaina👍を押しています

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

m.ts10806

2021/06/04 13:00

「そういう言語仕様」では納得できませんか
guest

回答3

0

long型の変数にも「l」を付与しなくても、そのまま代入できます。

long l = 1; // コンパイルOK

質問の意図は「l」はあるのになぜ「s」や「b」がないのか、ということだと解釈して回答します。
違ってたら無視してください。

Javaではリテラル同士の演算結果は、演算に使われたリテラルの型に依存します。
例えば、

System.out.print(10 / 3); // => 3 ---[1] System.out.print(2147483647 + 1); // => -2147483648 ---[2]

[1]はfloatかdoubleの結果が欲しいですし、[2]はlongの結果がほしいのですが、int型となるため正しい結果が得られません。
演算に使われたリテラルがどちらもint型だからです。
そこで、「f」や「l」をつけて、リテラルの型を変更します。

System.out.print(10f / 3); // => 3.3333333 ---[1] System.out.print(2147483647l + 1); // => 2147483648 ---[2]

演算結果は大きい方の型に合わせるので、[1]はfloat型に、[2]はlong型になります。

この問題はintで表現できない値の時のみ発生します。
そのため、「s」や「b」をつけて小さくするメリットがないのです。

投稿2021/06/04 14:15

irithyll

総合スコア14

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Monkuma

2021/06/05 00:01

>long型の変数にも「l」を付与しなくても、そのまま代入できます。 すみません、そうでした???? 正確にはlongサイズの値には[l]を付与しなければならない、ですね(追記いたします) >そのため、「s」や「b」をつけて小さくするメリットがないのです。 とても腑に落ちました!! そもそもl,d,fはintで表現できない値を表現したいときに使用するものでしたね。したがってs,bは必要がないと...。 ご回答ありがとうございました!
guest

0

ベストアンサー

Java言語仕様 (JLS) 5.2. Assignment Contextsを見ると、以下のように記述されています。

In addition, if the expression is a constant expression (§15.28) of type byte, short, char, or int:

A narrowing primitive conversion may be used if the type of the variable is byte, short, or char, and the value of the constant expression is representable in the type of the variable.

本来、精度の高い値を精度の低い型に代入する場合、明示的にキャストする必要があるのですが、short型やbyte型の変数にint型のリテラル値を代入するときはある種の特別扱いになっていて、Javaコンパイラが自動でキャストしてくれるわけです。

投稿2021/06/04 17:58

neko_the_shadow

総合スコア2349

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Monkuma

2021/06/05 00:29 編集

> A narrowing primitive conversion 「基本型の縮小変換が自動的に行われる」というのは恥ずかしながら初めて聞きました???? 回答ありがとうございます。
guest

0

irithyllさんの回答通りだと思いますが公式ドキュメントを見てみました。
明確には理由を書いていませんが、公式ドキュメントだとこの部分かな。

Integer Literals
An integer literal is of type long if it ends with the letter L or l; otherwise it is of type int. It is recommended that you use the upper case letter L because the lower case letter l is hard to distinguish from the digit 1.

Values of the integral types byte, short, int, and long can be created from int literals. Values of type long that exceed the range of int can be created from long literals. Integer literals can be expressed by these number systems:

投稿2021/06/04 14:27

kaina

総合スコア418

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Monkuma

2021/06/05 00:11

>Values of type long that exceed the range of int can be created from long literals. ありがとうございます!公式ドキュメント読めるようにします(^^) デフォルトがintリテラルなのにshort,byteに代入できる理由がよくわからなかったので助かりました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.35%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問