Javaのnullチェックでif文を使いたくない(解決せず)
解決した(2018/08/04 追加)
Javaのnullチェックでif文を使いたくない(個人的には解決) - ikhrのブログ
最近の悩み
public class TestNull { @SuppressWarnings("unused") public static void main(String[] args) { //何らかの処理の戻り値ParentBeanの値がnullと仮定 ParentBean parentBean = null; //悩みの種 if (parentBean != null && parentBean.getChildBean() != null) { System.out.println(parentBean.getChildBean().getGrandChildBean().getName()); } } }
Java SE8でOptionalというものが追加された
public class TestNull { public static void main(String[] args) { Optional<ParentBean> parentBean = Optional.ofNullable(null); //isPresent //今までと同じことに。。 //parentBeanの中身もOptionalでラップしてもらう必要がある。。※面倒臭いので割愛 if (parentBean.isPresent()) { System.out.println(parentBean.get().getChildBean().getGrandChildBean().getName()); } //ifPresent //これもやってること変わらない気がする。 parentBean.ifPresent(bean -> System.out.println(bean.getChildBean().getGrandChildBean().getName())); } }
参考
https://docs.oracle.com/javase/jp/8/docs/api/java/util/Optional.html
所感
Optionalは個々の実装で扱うものではないなと感じました。 今回悩みは解決に至りませんでした。
dateコマンドで前月の最終日を取得する
LAST_DAY=$(date -d “20171201+1month-1days” +%d)
export YM=$(date +%Y%m) LAST_DAY=$(date -d “${YM}01+1month-1days” +%d)
awkで変数を定義する
はじめに
ログ分析等でawk
を利用することが多い。どのサーバのログかが分かるよう、出力結果にホスト名等を含めたいことがある。試行錯誤(というほど考えていないが。。)した結果、pwd
の結果をawk
に渡すのが汎用的かなと思って、その紹介です。
pwd
単純にpwd
するとカレントディレクトリのフルパスになるので、カレントディレクトリだけ抜粋したい。
コマンド
$ pwd
結果
/Users/ユーザ名/Documents/blog_awk/host1
basename
ディレクトリ名を除いた文字列を返すコマンド。
コマンド
$ basename
結果
usage: basename string [suffix] basename [-a] [-s suffix] string [...]
pwd + basename + awk
コマンド
$ awk -v host=$(basename $(pwd)) '{print host, $1}' test.txt
結果
host1 aaa host1 bbb host1 ccc
Gradleのinitプラグインに触れた
Gradleには色々なプラグインが存在する。その中でタスク、ライフサイクルが定義されており、ちょっとしたことをする上で、これらの理解が必要となる雰囲気。この環境のGradleのバージョンは4.3である。
initプラグインがサポートするtypeはメッセージ的には次の通り。
この中の内、java-library
、java-application
、basic
についてディレクトリ構造とbuild.gradleファイルの内容を確認する。
Supported types: 'basic', 'groovy-application', 'groovy-library', 'java-application', 'java-library', 'pom', 'scala-library'.
java-libraryで作る
$ gradle init --type java-library BUILD SUCCESSFUL in 1s 2 actionable tasks: 2 executed $ tree . ├── build.gradle ├── gradle │ └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── gradlew ├── gradlew.bat ├── settings.gradle └── src ├── main │ └── java │ └── Library.java └── test └── java └── LibraryTest.java 7 directories, 8 files
java-libraryのbuild.gradle
$ cat build.gradle /* * This build file was generated by the Gradle 'init' task. * * This generated file contains a sample Java Library project to get you started. * For more details take a look at the Java Libraries chapter in the Gradle * user guide available at https://docs.gradle.org/4.3.1/userguide/java_library_plugin.html */ // Apply the java-library plugin to add support for Java Library apply plugin: 'java-library' // In this section you declare where to find the dependencies of your project repositories { // Use jcenter for resolving your dependencies. // You can declare any Maven/Ivy/file repository here. jcenter() } dependencies { // This dependency is exported to consumers, that is to say found on their compile classpath. api 'org.apache.commons:commons-math3:3.6.1' // This dependency is used internally, and not exposed to consumers on their own compile classpath. implementation 'com.google.guava:guava:23.0' // Use JUnit test framework testImplementation 'junit:junit:4.12' }
java-applicationで作る
ユーザーガイドでは--test-framework
の指定をしているが、無しで。
$ gradle init --type java-application Starting a Gradle Daemon (subsequent builds will be faster) BUILD SUCCESSFUL in 5s 2 actionable tasks: 2 executed $ tree . ├── build.gradle ├── gradle │ └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── gradlew ├── gradlew.bat ├── settings.gradle └── src ├── main │ └── java │ └── App.java └── test └── java └── AppTest.java 7 directories, 8 files
java-applicationのbuild.gradle
$ cat build.gradle /* * This build file was generated by the Gradle 'init' task. * * This generated file contains a sample Java project to get you started. * For more details take a look at the Java Quickstart chapter in the Gradle * user guide available at https://docs.gradle.org/4.3.1/userguide/tutorial_java_projects.html */ // Apply the java plugin to add support for Java apply plugin: 'java' // Apply the application plugin to add support for building an application apply plugin: 'application' // In this section you declare where to find the dependencies of your project repositories { // Use jcenter for resolving your dependencies. // You can declare any Maven/Ivy/file repository here. jcenter() } dependencies { // This dependency is found on compile classpath of this component and consumers. compile 'com.google.guava:guava:23.0' // Use JUnit test framework testCompile 'junit:junit:4.12' } // Define the main class for the application mainClassName = 'App'
applicationってそういうapplicationなのね。
basicで作る
$ gradle init --type basic BUILD SUCCESSFUL in 0s 2 actionable tasks: 2 executed $ tree . ├── build.gradle ├── gradle │ └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── gradlew ├── gradlew.bat └── settings.gradle 2 directories, 6 files
basicのbuild.gradle
$ cat build.gradle /* * This build file was generated by the Gradle 'init' task. * * This generated file contains a commented-out sample Java project to get you started. * For more details take a look at the Java Quickstart chapter in the Gradle * user guide available at https://docs.gradle.org/4.3.1/userguide/tutorial_java_projects.html */ /* // Apply the java plugin to add support for Java apply plugin: 'java' // In this section you declare where to find the dependencies of your project repositories { // Use 'jcenter' for resolving your dependencies. // You can declare any Maven/Ivy/file repository here. jcenter() } // In this section you declare the dependencies for your production and test code dependencies { // The production code uses the SLF4J logging API at compile time compile 'org.slf4j:slf4j-api:1.7.25' // Declare the dependency for your favourite test framework you want to use in your tests. // TestNG is also supported by the Gradle Test task. Just change the // testCompile dependency to testCompile 'org.testng:testng:6.8.1' and add // 'test.useTestNG()' to your build script. testCompile 'junit:junit:4.12' } */
所感
Gradeのプラグインを触りつつも、自分でGroovy書かないと、Gradleすげーってならない気がしてきた。
Macへコマンドをインストールする
Macへtree
とwget
をインストールした記録です。
Macへコマンドを追加する方法としてHomebrewと呼ばれるMac OS用のパッケージマネージャーがあるそうです。RedHat系Linuxで言うところのRPM、Yum等の仲間です。
Homebrewは奥さんがインストールを済ませておいたらしいので割愛します。
tree
を追加する。
$ brew install tree
Error: Cannot write to /usr/local/Cellar
世の中そんなに甘くないようで、エラーになりました。
ではsudo
で。
$ sudo brew install tree WARNING: Improper use of the sudo command could lead to data loss or the deletion of important system files. Please double-check your typing when using sudo. Type "man sudo" for more information. To proceed, enter your password, or type Ctrl-C to abort. Password: Error: Cowardly refusing to 'sudo brew install' You can use brew with sudo, but only if the brew executable is owned by root. However, this is both not recommended and completely unsupported so do so at your own risk.
親切設計。
brew
のオーナーがrootではなかった為、止めてくれました。
書き込めなかったディレクトリのオーナーを確認し、su
して再実行。
$ brew install tree ==> Downloading https://homebrew.bintray.com/bottles/tree-1.7.0.el_capitan.bottle.1.tar.gz ######################################################################## 100.0% ==> Pouring tree-1.7.0.el_capitan.bottle.1.tar.gz 🍺 /usr/local/Cellar/tree/1.7.0: 7 files, 112.4K
続いてwget
$ brew install wget ==> Installing dependencies for wget: openssl ==> Installing wget dependency: openssl ==> Downloading https://homebrew.bintray.com/bottles/openssl-1.0.2f.el_capitan.bottle.tar.gz ######################################################################## 100.0% ==> Pouring openssl-1.0.2f.el_capitan.bottle.tar.gz ==> Caveats A CA file has been bootstrapped using certificates from the system keychain. To add additional certificates, place .pem files in /usr/local/etc/openssl/certs and run /usr/local/opt/openssl/bin/c_rehash This formula is keg-only, which means it was not symlinked into /usr/local. Apple has deprecated use of OpenSSL in favor of its own TLS and crypto libraries Generally there are no consequences of this for you. If you build your own software and it requires this formula, you'll need to add to your build variables: LDFLAGS: -L/usr/local/opt/openssl/lib CPPFLAGS: -I/usr/local/opt/openssl/include ==> Summary 🍺 /usr/local/Cellar/openssl/1.0.2f: 466 files, 11.9M ==> Installing wget ==> Downloading https://homebrew.bintray.com/bottles/wget-1.17.1.el_capitan.bottle.1.tar.gz ######################################################################## 100.0% ==> Pouring wget-1.17.1.el_capitan.bottle.1.tar.gz 🍺 /usr/local/Cellar/wget/1.17.1: 9 files, 1.5M
少し賢くなりました。
Hello Gradle
Gradle日本語ドキュメントを見て手を動かす。
$ git clone https://github.com/ikhr/gradlestudy Cloning into 'gradlestudy'... warning: You appear to have cloned an empty repository. $ cd gradlestudy/ $ cat build.gradle task hello { doLast { println 'Hello world!' } } $ gradle -q hello Hello world!
せっかくなのでGitHubで管理しておきたい。
$ git add . $ git status On branch master Initial commit Changes to be committed: (use "git rm --cached <file>..." to unstage) new file: .gradle/4.3.1/fileChanges/last-build.bin new file: .gradle/4.3.1/fileHashes/fileHashes.bin new file: .gradle/4.3.1/fileHashes/fileHashes.lock new file: .gradle/4.3.1/taskHistory/taskHistory.lock new file: .gradle/buildOutputCleanup/buildOutputCleanup.lock new file: .gradle/buildOutputCleanup/cache.properties new file: build.gradle
邪魔そうなのがaddされてしまったので、addを取り消す。
$ git reset HEAD . fatal: ambiguous argument 'HEAD': unknown revision or path not in the working tree. Use '--' to separate paths from revisions, like this: 'git <command> [<revision>...] -- [<file>...]'
怒られてオプションを減らす。
$ git reset $ cat .gitignore # Gradle .gradle !gradle-wrapper.jar $ git add . $ git status On branch master Initial commit Changes to be committed: (use "git rm --cached <file>..." to unstage) new file: .gitignore new file: build.gradle $ git commit -m "first commit" [master (root-commit) 9fc8c18] first commit 2 files changed, 8 insertions(+) create mode 100644 .gitignore create mode 100644 build.gradle $ git push -u origin master Username for 'https://github.com': ikhr Password for 'https://ikhr@github.com': Counting objects: 4, done. Delta compression using up to 4 threads. Compressing objects: 100% (3/3), done. Writing objects: 100% (4/4), 331 bytes | 0 bytes/s, done. Total 4 (delta 0), reused 0 (delta 0) To https://github.com/ikhr/gradlestudy * [new branch] master -> master Branch master set up to track remote branch master from origin.
微妙に修正してcommitしてみる。
$ gradle -q hell Hello world!! $ git status On branch master Your branch is up-to-date with 'origin/master'. Changes not staged for commit: (use "git add <file>..." to update what will be committed) (use "git checkout -- <file>..." to discard changes in working directory) modified: build.gradle no changes added to commit (use "git add" and/or "git commit -a") $ git add build.gradle $ git status On branch master Your branch is up-to-date with 'origin/master'. Changes to be committed: (use "git reset HEAD <file>..." to unstage) modified: build.gradle $ git diff
add後のdiffは--cached
が必要。
$ git diff --cached diff --git a/build.gradle b/build.gradle index 153d849..3481f2b 100644 --- a/build.gradle +++ b/build.gradle @@ -1,5 +1,5 @@ task hello { doLast { - println 'Hello world!' + println 'Hello world!!' } }
GitHubへpushするのも四苦八苦
$ git push -u origin master Branch master set up to track remote branch master from origin. Everything up-to-date $ git status On branch master Your branch is up-to-date with 'origin/master'. Changes to be committed: (use "git reset HEAD <file>..." to unstage) modified: build.gradle $ git commit -m "commit" [master 71ff171] commit 1 file changed, 1 insertion(+), 1 deletion(-) $ git push origin master Counting objects: 3, done. Delta compression using up to 4 threads. Compressing objects: 100% (3/3), done. Writing objects: 100% (3/3), 319 bytes | 0 bytes/s, done. Total 3 (delta 0), reused 0 (delta 0) To https://github.com/ikhr/gradlestudy 9fc8c18..71ff171 master -> master