【Eclipse】コンパイルエラー/警告が発生する具体的ソースコード

### 【概要】
Eclipseの「ウィンドウ -> 設定 -> Java -> コンパイラー -> エラー/警告」でエラー/警告が発生する具体的なコードを書きました。
一部コードの書き方が分からない項目もありましたが、分からなかったものについてはソース上に「実装方法不明」とコメントしています。

### 【環境】
Java 17
Eclipse Version: 2023-06 (4.28.0)、Build id: 20230608-1333

### 【エラー/警告の一覧表】

下記表の項番はソースコードでコメントしている項番と一致しています。

#### コード・スタイル

| 項番 | エラー/警告 項目名 |
|:-----------|:------------|
| 1-1 | staticメンバーへの非staticアクセス |
| 1-2 | staticメンバーへの間接アクセス |
| 1-3 | インスタンス・フィールドへの限定されていないアクセス |
| 1-4 | エンクロージング型のアクセス不可メンバーへのアクセス |
| 1-5 | パラメータ代入 |
| 1-6 | 外部化されていないString(欠落している/未使用の$NON-NLS$タグ) |
| 1-7 | 何も記述のない空のブロック |
| 1-8 | try-with-resourceで管理されていないリソース(1.7以上) |
| 1-9 | コンストラクター名を持つメソッド |
| 1-10 | staticにできるメソッド |
| 1-11 | 潜在的にstaticにできるメソッド |

#### 潜在的なプログラミングの問題

| 項番 | エラー/警告 項目名 |
|:-----------|:------------|
| 2-1 | 同じ値の比較('x == x') |
| 2-2 | 効果のない代入(例:「x = x」) |
| 2-3 | 予期しない論理代入の可能性(たとえば、'if(a = b)') |
| 2-4 | ボクシングおよびアンボクシング変換 |
| 2-5 | ストリング連結での文字列配列の使用 |
| 2-6 | 可変長引数の型の一致が不正確 |
| 2-7 | ありそうもない'Object'を使用するコレクション・メソッドの引数型 |
| 2-7-1 | 予想される型に対して厳密な分析を実行する |
| 2-8 | ありそうもないequals()メソッドの引数型 |
| 2-9 | 空のステートメント |
| 2-10 | 未使用のオブジェクト割り振り |
| 2-11 | enumの不完全な'switch'ケース |
| 2-11-1 | 'default'ケースが存在する場合も知らせる |
| 2-12 | 'default'ケースが欠落した'switch' |
| 2-13 | 'switch'文のcaseのフォールスルー |
| 2-14 | 隠れたcatchブロック |
| 2-15 | 'finally'が正常に完了しない |
| 2-16 | デッド・コード(例:'if (false)') |
| 2-17 | リソース・リーク |
| 2-18 | 潜在的なリソース・リーク |
| 2-19 | serialVersionUIDなしのシリアライズ可能クラス |
| 2-20 | 継承されたメソッドのsynchronized修飾子の欠落 |
| 2-21 | 'equals()' をオーバーライドしているが 'hashCode()' がオーバーライドされていないクラス: |

#### 名前のシャドーイングおよび競合

| 項番 | エラー/警告 項目名 |
|:-----------|:------------|
| 3-1 | フィールド宣言が他のフィールドまたは変数を隠蔽 |
| 3-2 | ローカル変数宣言が他のフィールドまたは変数を隠蔽 |
| 3-2-1 | コンストラクターまたはsetterメソッド・パラメーターを含む |
| 3-3 | 型パラメーターが別の型を隠蔽 |
| 3-4 | メソッドがパッケージ可視メソッドを非オーバーライド |
| 3-5 | protectedの'Object'メソッドと競合するインターフェース・メソッド |

#### 使用すべきではない制限されたAPI

| 項番 | エラー/警告 項目名 |
|:-----------|:------------|
| 4-1 | 使用すべきではないAPI |
| 4-1-1 | 使用すべきではないコード内での使用すべきではないAPIの使用を知らせる |
| 4-1-2 | 使用すべきではないメソッドのオーバーライドまたは実装を知らせる |
| 4-2 | 除去とマークされた廃止予定のAPI |
| 4-3 | 禁止された参照(アクセス・ルール) |
| 4-4 | 阻止された参照(アクセス・ルール) |

#### モジュール

| 項番 | エラー/警告 項目名 |
|:-----------|:------------|
| 5-1 | APIリーク |
| 5-2 | 不安定な名前が必要な自動モジュール |

#### 不要なコード

| 項番 | エラー/警告 項目名 |
|:-----------|:------------|
| 6-1 | ローカル変数の値が未使用 |
| 6-2 | メソッド・パラメーターの値が未使用 |
| 6-2-1 | オーバーライドしたメソッドの実装を無視 |
| 6-3 | 未使用の型パラメーター |
| 6-4 | '@param'タグで未使用の文書化されたパラメーターを無視 |
| 6-5 | 例外パラメーターの値が未使用 |
| 6-6 | 未使用のインポート |
| 6-7 | 未使用のprivateメンバー |
| 6-8 | 不要な'else'ステートメント |
| 6-9 | 不要なキャストまたは'instansof'操作 |
| 6-10 | 不要な例外スロー宣言 |
| 6-10-1 | オーバーライドしたメソッドの実装を無視 |
| 6-10-2 | '@throws'または'@exception'で文書化された例外を無視 |
| 6-10-3 | 'Exception'および'Throwable'を無視 |
| 6-11 | 未使用の'break'または'continue'ラベル |
| 6-12 | 冗長なスーパー・インターフェース |

#### 総称型

| 項番 | エラー/警告 項目名 |
|:-----------|:------------|
| 7-1 | 未検査の総称型操作 |
| 7-2 | raw型の使用 |
| 7-3 | finalな型で制約された総称型パラメーター |
| 7-4 | 冗長な型引数(1.7以上) |
| 7-5 | raw APIが原因で避けられない総称型問題を無視 |

#### 注釈

| 項番 | エラー/警告 項目名 |
|:-----------|:------------|
| 8-1 | '@Override'注釈の欠落 |
| 8-1-1 | インターフェース・メソッドの実装を含める(1.6以上) |
| 8-2 | '@Deprecated'注釈の欠落 |
| 8-3 | 注釈をスーパー・インターフェースとして使用 |
| 8-4 | '@SuppressWarnings'で処理されないトークン |
| 8-5 | '@SuppressWarnings'注釈の使用可能化 |
| 8-5-1 | 未使用の'@SuppressWarnings'トークン |
| 8-5-2 | 関連するオプションが'無視'に設定され、完全には認識されない'未使用'ステータス |
| 8-5-3 | '@SuppressWarnings'でオプション・エラーを抑制 |

#### Null分析

| 項番 | エラー/警告 項目名 |
|:-----------|:------------|
| 9-1 | nullポインター・アクセス |
| 9-2 | 潜在的なnullポインター・アクセス |
| 9-3 | 冗長なnull検査 |
| 9-4 | null分析で'assert'を含める |
| 9-5 | 注釈ベースのnull分析を使用可能にする |
| 9-5-1 | null仕様違反 |
| 9-5-2 | null注釈およびnullインスタンスへの競合 |
| 9-5-3 | 非注釈型から@NonNull型への未検査変換 |
| 9-5-4 | 注釈付きのパラメーター化された型から注釈の少ないタイプへの安全でない変換 |
| 9-5-5 | 自由型変数のための悲観的な分析によって検出された問題 |
| 9-5-6 | ライブラリーからの自由型変数の安全でない'@Nonnull'の解釈 |
| 9-5-7 | 冗長なnull注釈 |
| 9-5-8 | オーバーライドするメソッドで注釈が付けられていない'@NonNull'パラメーター |
| 9-5-9 | パッケージの'@NonNullByDefault'注釈が欠落 |
| 9-5-10 | null仕様のデフォルト注釈を使用する |
| 9-5-11 | null注釈の継承 |
| 9-5-12 | フィールドの構文null分析を使用可能にする |
| 9-5-13 | すべてのビルド・パス・ロケーションで外部注釈を検索する |



### 【GitHubにアップロードしたプロジェクト構成】

https://github.com/nobu12/eclipse-compiler-errors-warnings

- errors-warnings
  - Null分析以外のソースコード
- errors-warnings-null-analysis
  - Null分析だけのソースコード（@org.eclipse.jdt.annotation.NonNullを使用するには、Springプロジェクトで作成する必要があったため）
- unstableAutoModuleName
  - モジュールで利用するためのjar作成用のソースコード

### 【ソースコード】

#### errors-warningsプロジェクト

<details><summary>コード・スタイル</summary>

```java:CodeStyle.java
package codestyle;

import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;

public class CodeStyle extends CodeStyleParent {

	private static final int CODE_STYLE = 0;

	private void indirectStaticAccess() {
		CodeStyle codeStyle = new CodeStyle();
		// 1-1. staticメンバーへの非staticアクセス
		int a = codeStyle.CODE_STYLE;
	}

	private void staticAccessReceiver() {
		// 1-2. staticメンバーへの間接アクセス
		int a = CodeStyle.CODE;
	}

	private int codeStyle;

	private void unqualifiedFieldAccess() {
		// 1-3. インスタンス・フィールドへの限定されていないアクセス
		int a = codeStyle;
	}

	private void syntheticAccessEmulation() {
		EnclosingClass ec = new EnclosingClass();
		// 1-4. エンクロージング型のアクセス不可メンバーへのアクセス
		// おそらくJava8以前のバージョンにしないとエラー/警告が起きない
		// 少なくともJava8のバージョンではエラー/警告が起きることを確認済み
		int a = ec.a;
	}

	class EnclosingClass {
		private int a;
		int b;
	}

	private void parameterAssignment(int a) {
		// 1-5. パラメータ代入
		a = 1;
	}

	private void nonExternalizedStringLiteral() {
		// 1-6. 外部化されていないString(欠落している/未使用の$NON-NLS$タグ)
		String a = "a";
		int b = 1; //$NON-NLS-1$
	}

	private void undocumentedEmptyBlock(boolean can) {
		// 1-7. 何も記述のない空のブロック
		if (true) {
		}
	}

	private void explicitlyClosedAutoCloseable() throws IOException {
		// 1-8. try-with-resourceで管理されていないリソース(1.7以上)
		BufferedReader reader = new BufferedReader(new InputStreamReader(new FileInputStream(".classpath"), "UTF-8"));
		try {
			String line;
			while ((line = reader.readLine()) != null) {
				System.out.println(line);
			}
		} catch (IOException e) {
			throw e;
		} finally {
			try {
				reader.close();
			} catch (IOException e) {
				throw e;
			}
		}
	}

	// 1-9. コンストラクター名を持つメソッド
	private void CodeStyle() {
	}

	// 1-10. staticにできるメソッド
	private void reportMethodCanBeStatic() {
		int a = 1;
	}

	// 1-11. 潜在的にstaticにできるメソッド
	public void reportMethodCanBePotentiallyStatic() {
		int a = CodeStyle.CODE;
	}
}
```

```java:CodeStyleParent.java
package codestyle;

public class CodeStyleParent {
	public static final int CODE = 1;
}
```

</details>

<details><summary>潜在的なプログラミングの問題</summary>

```java:ProgrammingProblem.java
package programmingproblem;

import java.io.BufferedReader;
import java.io.CharConversionException;
import java.io.Closeable;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.Serializable;
import java.io.UncheckedIOException;
import java.nio.file.DirectoryIteratorException;
import java.nio.file.DirectoryStream;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Spliterator;
import java.util.Spliterators;
import java.util.stream.Stream;
import java.util.stream.StreamSupport;

// 2-21. 'equals()'をオーバーライドしているが'hashCode()'がオーバーライドされていないクラス
public class ProgrammingProblem extends ProgrammingProblemParent {
	private void comparingIdentical(int a) {
		// 2-1. 同じ値の比較('x == x')
		if (a == a) {
		}
	}

	private void noEffectAssignment(int a) {
		// 2-2. 効果のない代入(例:「x = x」)
		a = a;
	}

	private void possibleAccidentalBooleanAssignment(boolean a, boolean b) {
		// 2-3. 予期しない論理代入の可能性(たとえば、'if(a = b)')
		if (a = b) {
		}
	}

	private void autoboxing(int a, Integer b) {
		// 2-4. ボクシングおよびアンボクシング変換
		// ボクシング変換
		Integer c = a;
		// アンボクシング変換
		int d = b;
	}

	private void noImplicitStringConversion() {
		// 2-5. ストリング連結での文字列配列の使用
		String a = "hello" + new char[] { 'w', 'o', 'r', 'l', 'd' };
	}

	private void varargsArgumentNeedCast() {
		// 2-6. 可変長引数の型の一致が不正確
		Arrays.asList(null);
	}

	private void unlikelyCollectionMethodArgumentType() {
		Map<String, String> a = new HashMap<>();
		// 2-7. ありそうもない'Object'を使用するコレクション・メソッドの引数型
		a.get(1);
	}
	
	private void unlikelyCollectionMethodArgumentTypeStrict(Object o) {
		Map<?, ?> a = new HashMap<>();
		// 2-7-1. 予想される型に対して厳密な分析を実行する にチェックあり
		a.get(o);
	}

	private void unlikelyEqualsArgumentType(Collection<Path> aaa) {
		// 2-8. ありそうもないequals()メソッドの引数型
		"abc".equals(1);
	}

	private void emptyStatement() {
		// 2-9. 空のステートメント
		;
	}

	private void unusedObjectAllocation() {
		// 2-10. 未使用のオブジェクト割り振り
		new ArrayList<>();
	}

	private enum Color {
		RED, GREEN, BLUE
	}

	private void incompleteEnumSwitch(Color color) {
		// 2-11. enumの不完全な'switch'ケース
		switch (color) {
		case RED:
			System.out.println("赤");
			break;
		case GREEN:
			System.out.println("緑");
			break;
		}

		// 2-11-1. 'default'ケースが存在する場合も知らせる にチェックあり
		switch (color) {
		case RED:
			System.out.println("赤");
			break;
		case GREEN:
			System.out.println("緑");
			break;
		default:
			System.out.println("その他");
		}
	}

	private void missingDefaultCase(Color color) {
		// 2-12. 'default'ケースが欠落した'switch'
		switch (color) {
		case RED:
			System.out.println("赤");
			break;
		case GREEN:
			System.out.println("緑");
			break;
		}
	}

	private void fallthroughCase(Color color) {
		switch (color) {
		case RED:
			System.out.println("赤");
		// 2-13. 'switch'文のcaseのフォールスルー
		case GREEN:
			System.out.println("緑");
			break;
		}
	}

	private void hiddenCatchBlock() {
		try {
			throw new CharConversionException();
		} catch (CharConversionException e) {
		// 2-14. 隠れたcatchブロック
		} catch (IOException e) {
		}
	}

	private void finallyBlockNotCompletingNormally() throws IOException {
		BufferedReader reader = new BufferedReader(new InputStreamReader(new FileInputStream(".classpath"), "UTF-8"));
		try {
			String line;
			while ((line = reader.readLine()) != null) {
				System.out.println(line);
			}
		} catch (IOException e) {
			throw e;
		// 2-15. 'finally'が正常に完了しない
		} finally {
			try {
				reader.close();
				return;
			} catch (IOException e) {
				throw e;
			}
		}
	}

	private void deadCode() {
		if (true) {
		// 2-16. デッド・コード(例:'if (false)')
		} else {
		}
	}

	private void unclosedCloseable() throws IOException {
		// 2-17. リソース・リーク
		BufferedReader reader = new BufferedReader(new InputStreamReader(new FileInputStream(".classpath"), "UTF-8"));
		try {
			String line;
			while ((line = reader.readLine()) != null) {
				System.out.println(line);
			}
		} catch (IOException e) {
			throw e;
		}
	}
	
	// java.nio.file.Filesのlist(Path dir)の実装をそのままコピーしたもの
	private Stream<Path> potentiallyUnclosedCloseable(Path dir) throws IOException {
        DirectoryStream<Path> ds = Files.newDirectoryStream(dir);
        try {
            final Iterator<Path> delegate = ds.iterator();

            // Re-wrap DirectoryIteratorException to UncheckedIOException
            Iterator<Path> iterator = new Iterator<>() {
                @Override
                public boolean hasNext() {
                    try {
                        return delegate.hasNext();
                    } catch (DirectoryIteratorException e) {
                        throw new UncheckedIOException(e.getCause());
                    }
                }
                @Override
                public Path next() {
                    try {
                        return delegate.next();
                    } catch (DirectoryIteratorException e) {
                        throw new UncheckedIOException(e.getCause());
                    }
                }
            };

            Spliterator<Path> spliterator =
                Spliterators.spliteratorUnknownSize(iterator, Spliterator.DISTINCT);
            // 2-18. 潜在的なリソース・リーク
            return StreamSupport.stream(spliterator, false)
                                .onClose(asUncheckedRunnable(ds));
        } catch (Error|RuntimeException e) {
            try {
                ds.close();
            } catch (IOException ex) {
                try {
                    e.addSuppressed(ex);
                } catch (Throwable ignore) {}
            }
            throw e;
        }
	}
	
    private static Runnable asUncheckedRunnable(Closeable c) {
        return () -> {
            try {
                c.close();
            } catch (IOException e) {
                throw new UncheckedIOException(e);
            }
        };
    }
	

	// 2-19. serialVersionUIDなしのシリアライズ可能クラス
	private class MissingSerialVersion implements Serializable {
	}

	@Override
	// 2-20. 継承されたメソッドのsynchronized修飾子の欠落
	protected void synchronizedMethod() {
	}

	@Override
	public boolean equals(Object obj) {
		return true;
	}
}
```

```java:ProgrammingProblemParent.java
package programmingproblem;

public class ProgrammingProblemParent {
	protected synchronized void synchronizedMethod() {
	}
}

```

</details>

<details><summary>名前のシャドーイングおよび競合</summary>

```java:NameShadow.java
package nameshadow;

import nameshadow.override.NameShadowParent;

public class NameShadow extends NameShadowParent {
	// 3-1. フィールド宣言が他のフィールドまたは変数を隠蔽
	private int a;

	private void localVariableHiding() {
		// 3-2. ローカル変数宣言が他のフィールドまたは変数を隠蔽
		int a;
	}

	// 3-2-1. コンストラクターまたはsetterメソッド・パラメーターを含む にチェックあり
	private NameShadow(int a) {
	}

	// 3-3. 型パラメーターが別の型を隠蔽
	private class Outer<T> {
		class Inner<T> {
		}
	}

	// 3-4. メソッドがパッケージ可視メソッドを非オーバーライド
	void overridingPackageDefaultMethod() {
	}
}
```

```java:NameShadowParent.java
package nameshadow.override;

public abstract class NameShadowParent {
	protected int a;
	
	void overridingPackageDefaultMethod() {
	}
}
```

```java:NameShadowInterface.java
package nameshadow;

public interface NameShadowInterface {
	// 3-5. protectedの'Object'メソッドと競合するインターフェース・メソッド
	int clone();
}
```

</details>

<details><summary>使用すべきではない制限されたAPI</summary>

```java:DeprecatedApi.java
package deprecatedapi;

import java.net.MalformedURLException;
import java.net.URI;
import java.net.URISyntaxException;
import java.net.URL;

public class DeprecatedApi extends DeprecatedApiParent {
	private void deprecation() {
		// 4-1. 使用すべきではないAPI
		Character.isJavaLetter('a');
	}
	
	
	@Deprecated
	public void deprecationInDeprecatedCode() {
		// 4-1-1. 使用すべきではないコード内での使用すべきではないAPIの使用を知らせる にチェックあり
		super.deprecationWhenOverridingDeprecatedMethod();
	}
	
	@Override
	// 4-1-2. 使用すべきではないメソッドのオーバーライドまたは実装を知らせる にチェックあり
	public void deprecationWhenOverridingDeprecatedMethod() {
	}
	
	// 4-2. 除去とマークされた廃止予定のAPI は実装方法不明
	
	private void forbiddenReference() throws URISyntaxException {
		// 4-3. 禁止された参照(アクセス・ルール)
		// ビルドパスのアクセスルールに追加が必要
		URI uri = new URI("https://qiita.com");
	}
	
	private void discouragedReference() throws MalformedURLException  {
		// 4-4. 阻止された参照(アクセス・ルール)
		// ビルドパスのアクセスルールに追加が必要
		URL url = new URL("https://qiita.com");
	}
}
```

```java:DeprecatedApiParent.java
package deprecatedapi;

public class DeprecatedApiParent {
	@Deprecated
	public void deprecationWhenOverridingDeprecatedMethod() {
	}
}
```

</details>

<details><summary>モジュール</summary>

```java:Module.java
package modules;

public class Module {
	
	// 5-1. APIリーク
	public ApiLeak apiLeak() {
		return new ApiLeak();
	}
	
	private class ApiLeak {
	}
}
```

```java:module-info.java
module modules {
	exports modules;
	// 5-2. 不安定な名前が必要な自動モジュール
	requires unstableAutoModuleName;
}
```

</details>

<details><summary>不要なコード</summary>

```java:UnNecessaryCode.java
package unnecessarycode;

import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.List;
// 6-6. 未使用のインポート
// ファイル保存時に不要なインポートが自動削除される場合があるため、コメントアウトしている
// 警告確認時はコメントアウトを外す必要がある
// import java.util.regex.Matcher;

//6-12. 冗長なスーパー・インターフェース
public class UnNecessaryCode extends UnNecessaryCodeParent implements UnNecessaryCodeInterface {

	private void unusedLocal() {
		// 6-1. ローカル変数の値が未使用
		int a;
	}

	// 6-2. メソッド・パラメーターの値が未使用
	private void unusedParameter(int a) {
	}

	@Override
	// 6-2-1. オーバーライドしたメソッドの実装を無視 にチェックなし
	public void unusedParameterWhenOverridingConcrete(int a) {
	}

	// 6-3. 未使用の型パラメーター
	private <E> void unusedTypeParameter(List<?> list) {
	}

	/**
	 * 
	 * @param <E>
	 * @param list
	 */
	// 6-3. 未使用の型パラメーター
	// 6-4. '@param'タグで未使用の文書化されたパラメーターを無視 にチェックなし
	private <E> void unusedParameterIncludeDocCommentReference(List<?> list) {
	}

	private void unusedExceptionParameter() {
		try (BufferedReader twrReader = new BufferedReader(
				new InputStreamReader(new FileInputStream(".classpath"), "UTF-8"));) {
			String line;
			while ((line = twrReader.readLine()) != null) {
				System.out.println(line);
			}
		// 6-5. 例外パラメーターの値が未使用
		} catch (IOException e) {
		}
	}
	
	// 6-7. 未使用のprivateメンバー
	private int a;

	private void unnecessaryElse() {
		if (true) {
			return;
		// 6-8. 不要な'else'ステートメント
		} else {
		}
	}

	private void unnecessaryTypeCheck() {
		// 6-9. 不要なキャストまたは'instansof'操作
		int a = (int) 1;
	}

	// 6-10. 不要な例外スロー宣言
	private void unusedDeclaredThrownException() throws IOException {
	}

	@Override
	// 6-10-1. オーバーライドしたメソッドの実装を無視 にチェックなし
	public void unusedDeclaredThrownExceptionWhenOverriding() throws IOException {
	}
	
	/**
	 * 
	 * @throws IOException
	 */
	// 6-10-2. '@throws'または'@exception'で文書化された例外を無視 にチェックなし
	private void unusedDeclaredThrownExceptionIncludeDocCommentReference() throws IOException {
	}

	// 6-10-3. 'Exception'および'Throwable'を無視 にチェックなし
	private void unusedDeclaredThrownExceptionExemptExceptionAndThrowable() throws Exception {
	}

	// 6-11. 未使用の'break'または'continue'ラベル
	private void unusedLabel() {
		label: for (int i = 1; i < 10; i++) {
		}
	}
}
```

```java:UnNecessaryCodeParent.java
package unnecessarycode;

import java.io.IOException;

public class UnNecessaryCodeParent implements UnNecessaryCodeInterface {
	public void unusedParameterWhenOverridingConcrete(int a) {
	}
	
	public void unusedDeclaredThrownExceptionWhenOverriding() throws IOException {
	}

	@Override
	public void redundantSuperinterface() {
	}
}
```

```java:UnNecessaryCodeInterface.java
package unnecessarycode;

public interface UnNecessaryCodeInterface {
	public void redundantSuperinterface();
}
```

</details>

<details><summary>総称型</summary>

```java:Generics.java
package generics;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

public class Generics extends GenericsParent {
	private void uncheckedTypeOperation() {
		// 7-1. 未検査の総称型操作
		List<Integer> a = new ArrayList(Arrays.asList(1));
	}

	private void rawTypeReference() {
		// 7-2. raw型の使用
		List a;
	}

	// 7-3. finalな型で制約された総称型パラメーター
	private <T extends String> T finalParameterBound() {
		return null;
	}

	private void redundantSpecificationOfTypeArguments() {
		// 7-4. 冗長な型引数(1.7以上)
		List<Integer> a = new ArrayList<Integer>();
	}

	@Override
	// 7-2. raw型の使用
	// 7-5. raw APIが原因で避けられない総称型問題を無視 にチェックなし
	public void unavoidableGenericTypeProblems(ArrayList list) {
	}
}
```

```java:GenericsParent.java
package generics;

import java.util.ArrayList;

public class GenericsParent {
	public void unavoidableGenericTypeProblems(ArrayList list) {
	}
}
```

</details>

<details><summary>注釈</summary>

```java:Annotation.java
package annotation;

public class Annotation extends AnnotationParent implements AnnotationInterface {

	// 8-1. '@Override'注釈の欠落
	public void missingOverrideAnnotation() {
	}
	
	// 8-1-1. インターフェース・メソッドの実装を含める(1.6以上) にチェックあり
	public void missingOverrideAnnotationForInterfaceMethodImplementation() {
	}

	/**
	 * @deprecated
	 */
	// 8-2. '@Deprecated'注釈の欠落
	private void missingDeprecatedAnnotation() {
	}

	// 8-4. '@SuppressWarnings'で処理されないトークン
	@SuppressWarnings(value = { "test" })
	private void unhandledWarningToken() {
	}

	// 8-5. '@SuppressWarnings'注釈の使用可能化
	@SuppressWarnings("deprecation")
	private void suppressWarnings() {
		Character.isJavaLetter('a');
	}

	// 8-5. '@SuppressWarnings'注釈の使用可能化 にチェックあり
	// 8-5-1. 未使用の'@SuppressWarnings'トークン
	@SuppressWarnings("deprecation")
	private void unusedWarningToken() {
	}

	// 6-7. 未使用のprivateメンバー を"無視"に設定
	// 8-5. '@SuppressWarnings'注釈の使用可能化 にチェックあり
	// 8-5-2. 関連するオプションが'無視'に設定され、完全には認識されない'未使用'ステータス
	@SuppressWarnings("unused")
	private void suppressWarningsNotFullyAnalysed() {
	}

	@SuppressWarnings("all")
	private void suppressOptionalErrors(int a) {
		// 2-1. 同じ値の比較('x == x')
		// 8-5. '@SuppressWarnings'注釈の使用可能化 にチェックあり
		// 8-5-3. '@SuppressWarnings'でオプション・エラーを抑制 にチェックなし
		if (a == a) {
		}
	}
	
	@Override
	public Class<? extends java.lang.annotation.Annotation> annotationType() {
		return null;
	}
}
```

```java:AnnotationParent.java
package annotation;

public class AnnotationParent {
	public void missingOverrideAnnotation() {
	}
}
```

```java:AnnotationInterface.java
package annotation;

// 8-3. 注釈をスーパー・インターフェースとして使用
public interface AnnotationInterface extends Override {
	public void missingOverrideAnnotationForInterfaceMethodImplementation();
}
```

</details>

#### errors-warnings-null-analysisプロジェクト

<details><summary>Null分析</summary>

```java:NullAnalysis.java
package com.example.demo.nullanalysis;

import java.util.ArrayList;
import java.util.List;

import org.eclipse.jdt.annotation.NonNullByDefault;

public class NullAnalysis {
	private void nullReference() {
		String a = null;
		// 9-1. nullポインター・アクセス
		a.length();
	}

	private void potentialNullReference(String a) {
		boolean isNull = a == null;
		if (isNull) {
			// 9-2. 潜在的なnullポインター・アクセス
			a.length();
		}
	}
	
	private void redundantNullCheck() {
		String a = "test";
		int b = a.length();
		// 9-3. 冗長なnull検査
	    if (a == null) {
	    }
	}
	
	private void includeNullInfoFromAsserts(String a) {
	    assert a != null;
	    // 9-3. 冗長なnull検査
	    // 9-4. null分析で'assert'を含める
	    if (a != null) {
	    }
	}
	
	private void nullSpecViolation(@org.eclipse.jdt.annotation.NonNull String a) {
    	// 9-5-1. null仕様違反
    	a = null;
    }

	private void nullAnnotationInferenceConflict(boolean can) {
		@org.eclipse.jdt.annotation.NonNull
		String a = "a";
		String b = "b";
		
		if (can) {
			b = null;
		}
		
		// 9-5-2. null注釈およびnullインスタンスへの競合
		a = b;
    }
    
	private void nullUncheckedConversion(boolean can) {
		@org.eclipse.jdt.annotation.NonNull
		String a;
		
		if (can) {
			// 9-5-3. 非注釈型から@NonNull型への未検査変換
			a = nullUncheckedConversionSub();
		}
    }
    
	private String nullUncheckedConversionSub() {
    	return null;
    }
    
	private void annotatedTypeArgumentToUnannotated() {
    	List<@org.eclipse.jdt.annotation.NonNull String> a = new ArrayList<>();
    	List<String> b = new ArrayList<>();
    	
    	// 9-5-4. 注釈付きのパラメーター化された型から注釈の少ないタイプへの安全でない変換
    	b = a;
    }
    
	private class PessimisticNullAnalysisForFreeTypeVariables<T extends Number> {
		int consume(T a) {
			// 9-5-5. 自由型変数のための悲観的な分析によって検出された問題
			return a.intValue();
		}

		T provide() {
			// 9-5-5. 自由型変数のための悲観的な分析によって検出された問題
			return null;
		}
	}
	
	// 9-5-6. ライブラリーからの自由型変数の安全でない'@Nonnull'の解釈 は実装方法不明
	
	@NonNullByDefault
	private class RedundantNullAnnotation {
		// 9-5-7. 冗長なnull注釈
		@org.eclipse.jdt.annotation.NonNull
		public String redundantNullAnnotation() {
			return "a";
		}
	}
	
	@NonNullByDefault
	private class NonnullParameterAnnotationDroppedParent {
		public void nonnullParameterAnnotationDropped(String a) {
		}
	}
	
	private class NonnullParameterAnnotationDropped extends NonnullParameterAnnotationDroppedParent {
		@Override
		// 9-5-8. オーバーライドするメソッドで注釈が付けられていない'@NonNull'パラメーター
		// 9-5-11. null注釈の継承 にチェックを付けるとエラーがなくなる
		public void nonnullParameterAnnotationDropped(String a) {
		}
	}
	
	@org.eclipse.jdt.annotation.Nullable
	private Object a;

	private void syntacticNullAnalysisForFields() {
		if (a != null)
			// 9-2. 潜在的なnullポインター・アクセス
			// 9-5-12. フィールドの構文null分析を使用可能にする にチェックを付けるとエラーがなくなる
			a.toString();
	}
	
	// 9-5-13. すべてのビルド・パス・ロケーションで外部注釈を検索する は実装方法不明
}
```

```java:MissingNonNullByDefaultAnnotation.java
// 9-5-9. パッケージの'@NonNullByDefault'注釈が欠落
public class MissingNonNullByDefaultAnnotation {

}
```

</details>

### 【必要だったプロジェクト設定】

#### 使用すべきではない制限されたAPI

下記項目についてはアクセス・ルールの追加が必要でした。

- 4-3. 禁止された参照(アクセス・ルール)
- 4-4. 阻止された参照(アクセス・ルール)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/121997/8eed8aca-f1ce-41b0-f426-4042a20b5ba7.png)


#### モジュール

下記項目についてはunstableAutoModuleNameプロジェクトをjarにして、外部jarの追加が必要でした。

- 5-2. 不安定な名前が必要な自動モジュール

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/121997/5635d47e-3c8b-8475-e9f9-1c0dfd7683fd.png)


### 【参考サイト】
- [Java コンパイルのエラー/警告設定](https://www.ibm.com/docs/ja/rational-soft-arch/9.6.1?topic=compiler-errorswarnings)
- [Java Compile Errors/Warnings Preferences](https://help.eclipse.org/latest/index.jsp?topic=%2Forg.eclipse.jdt.doc.user%2Freference%2Fpreferences%2Fjava%2Fcompiler%2Fref-preferences-errors-warnings.htm)
- [org.eclipse.jdt.core.JavaCore](https://help.eclipse.org/latest/index.jsp?topic=%2Forg.eclipse.jdt.doc.isv%2Freference%2Fapi%2Forg%2Feclipse%2Fjdt%2Fcore%2FJavaCore.html)
- [NULL 注釈の使用](https://www.ibm.com/docs/ja/developer-for-zos/9.1.1?topic=quality-using-null-annotations)