diff --git a/kadai2/README.md b/kadai2/README.md new file mode 100644 index 0000000..71b6be2 --- /dev/null +++ b/kadai2/README.md @@ -0,0 +1,47 @@ +# 課題2-1 + +## 課題 + +* io.Readerとio.Writerについて調べてみよう + * 標準パッケージでどのように使われているか + * io.Readerとio.Writerがあることでどういう利点があるのか具体例を挙げて考えてみる + +## 回答 + +参照したコード + +* https://github.com/golang/go/blob/master/src/io/io.go +* https://github.com/golang/go/blob/master/src/bytes/buffer.go +* https://github.com/golang/go/blob/master/src/bytes/reader.go +* https://github.com/golang/go/blob/master/src/archive/zip/reader.go +* https://github.com/golang/go/blob/master/src/archive/zip/writer.go + +### どのように使われているか + +* io.go + * io.goRead、Write、Close、Seek等に対してそれぞれInterfaceが定義されている + * ReadWriter、ReadCloser等複数の振る舞いに対しては型埋め込みが使われている +* bytes/buffer.go, bytes/reader.go + * io.goでintefaceとして定義されたByteReaderのメソッド `ReadByte` の振る舞いをそれぞれ記述していた +* zip/reader.go, zip/writer.go + * ... + +### どういう利点があるのか + +* ??? + +--- + +# 課題2-2 + +## 課題 + +* 1回目の宿題のテストを作ってみて下さい + * テストのしやすさを考えてリファクタリングしてみる + * テストのカバレッジを取ってみる + * テーブル駆動テストを行う + * テストヘルパーを作ってみる + +## 回答 + +W.I.P... diff --git a/kadai2/imgconvert/.gitignore b/kadai2/imgconvert/.gitignore new file mode 100644 index 0000000..30e04dd --- /dev/null +++ b/kadai2/imgconvert/.gitignore @@ -0,0 +1 @@ +outputs/* diff --git a/kadai2/imgconvert/.gitkeep b/kadai2/imgconvert/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/kadai2/imgconvert/README.md b/kadai2/imgconvert/README.md new file mode 100644 index 0000000..75cd8c0 --- /dev/null +++ b/kadai2/imgconvert/README.md @@ -0,0 +1,82 @@ +# 課題1 - 画像変換コマンドを作ろう - + +以下の仕様を満たすコマンドを作る。 + +- ディレクトリを指定する +- 指定したディレクトリ以下のJPGファイルをPNGに変換 +- ディレクトリ以下は再帰的に処理する +- 変換前と変換後の画像形式を指定できる + +また以下を満たすように実装すること + +- mainパッケージと分離する +- 自作パッケージと標準パッケージと準標準パッケージのみ使う + - 準標準パッケージ:golang.org/x以下のパッケージ +- ユーザ定義型を作ってみる +- GoDocを生成してみる + +# 実行手順 + +以下のコマンドでビルドする。 + +``` +# ビルド +go build -o myconverter + +# 出力用フォルダを作成する +mkdir outputs +``` + +ディレクトリは`-target`で指定し、`-from`で変更前の拡張子、`-to`で変更後の拡張子を指定する。変換されたファイルはoutputフォルダに出力される。 + +``` +# images配下のjpgファイルをpngへ変換する +$ ./myconverter -target=images -from=jpg -to=png +Convert Success from images/dir/sub_lena.jpg to outputs/sub_lena.png +Convert Success from images/lena.jpg to outputs/lena.png + +# images配下のpngファイルをjpgへ変換する +$ ./myconverter -target=images -from=png -to=jpg +Convert Success from images/dir/sub_icon.png to outputs/sub_icon.jpg +Convert Success from images/icon.png to outputs/icon.jpg +``` + +デフォルトでは`target`はカレントディレクトリが指定され、`jpg`から`png`への変換を実行する。 +``` +$ ./myconverter +Convert Success from current_rena.jpg to outputs/current_rena.png +Convert Success from images/dir/sub_lena.jpg to outputs/sub_lena.png +Convert Success from images/lena.jpg to outputs/lena.png +``` + +`jpg`から`png`、`png`から`jpg`への変換のみサポートしており、その他の変換には失敗する。 +``` +$ ./myconverter -target=images -from=gif -to=jpg +[ERROR]No supprot to convert from gif to jpg +``` + +ヘルプコマンド +``` +# ヘルプコマンドの実行例 +$ ./myconverter -h +Usage of ./myconverter: + -from string + from file extention (default "jpg") + -target string + target filepath. (default ".") + -to string + to file extention (default "png") +``` + +godocを生成してみる +``` +$godoc -html ./converter > godoc-converter.html +``` + +--- + +# 所感 + +- 以前入れ忘れたVSCodeのGoプラグインを入れた結果、GoLintによってコンパイル実行前に型エラーに気づけたり、GoDocの記入漏れに気づくことができた +- まだGoに書きなれてないので文法をググりながらやったので時間がかかってしまった +- GoDocの生成のときにgithub.comから参照しようとしたがブランチを参照する方法が分からなかった diff --git a/kadai2/imgconvert/converter/converter.go b/kadai2/imgconvert/converter/converter.go new file mode 100644 index 0000000..d2a9582 --- /dev/null +++ b/kadai2/imgconvert/converter/converter.go @@ -0,0 +1,128 @@ +// Package converter Overview +package converter + +import ( + "fmt" + "image" + "image/jpeg" + "image/png" + "os" + "path/filepath" +) + +// MyImageFile contains fileExt, filepath before converted, and after converted. +type MyImageFile struct { + fileExt string // file extension + fromFilepath string // from filepath + toFilepath string // to filepath +} + +// ConvertImagesFromJpgToPngInDir converts all jpg images to png in target directory. +func ConvertImagesFromJpgToPngInDir(dir string) { + for _, path := range GetFilepathListByExt(dir, ".jpg") { + myImageFile := MyImageFile{fileExt: "jpg", fromFilepath: path, toFilepath: ""} + if err := ConvertJpgToPng(&myImageFile); err != nil && myImageFile.fileExt == "png" { + fmt.Println("[ERROR] Convert failed from jpg to png.") + } else { + fmt.Println("Convert Success from " + myImageFile.fromFilepath + " to " + myImageFile.toFilepath) + } + } +} + +// ConvertImagesFromPngToJpgInDir converts all png images to jpg in target directory. +func ConvertImagesFromPngToJpgInDir(dir string) { + for _, path := range GetFilepathListByExt(dir, ".png") { + myImageFile := MyImageFile{fileExt: "png", fromFilepath: path, toFilepath: ""} + if err := ConvertPngToJpg(&myImageFile); err != nil && myImageFile.fileExt == "jpg" { + fmt.Println("[ERROR] Convert failed from png to jpg.") + } else { + fmt.Println("Convert Success from " + myImageFile.fromFilepath + " to " + myImageFile.toFilepath) + } + } +} + +// GetFilepathListByExt returns the filepath list by the extention in target directory. +func GetFilepathListByExt(dir string, ext string) []string { + filePathList := make([]string, 0) + err := filepath.Walk(dir, func(path string, info os.FileInfo, err error) error { + if filepath.Ext(path) == ext { + filePathList = append(filePathList, path) + } + return nil + }) + + if err != nil { + return nil + } + + return filePathList +} + +// ConvertJpgToPng convert target jpg image to png. +func ConvertJpgToPng(imageFile *MyImageFile) error { + file, err := os.Open(imageFile.fromFilepath) + if err != nil { + fmt.Println("[ERROR] No Such File.") + return err + } + defer file.Close() + + outputFilePath := "outputs/" + GetFileNameWithoutExt(imageFile.fromFilepath) + ".png" + + img, _, err := image.Decode(file) + + dstfile, err := os.Create(outputFilePath) + if err != nil { + fmt.Println("[ERROR] No Such FilePath.") + return err + } + defer dstfile.Close() + + err = jpeg.Encode(dstfile, img, nil) + if err != nil { + fmt.Println("[ERROR] File Encode Failed.") + return err + } + + imageFile.fileExt = "png" + imageFile.toFilepath = outputFilePath + + return nil +} + +// ConvertPngToJpg convert target png image to jpg. +func ConvertPngToJpg(imageFile *MyImageFile) error { + file, err := os.Open(imageFile.fromFilepath) + if err != nil { + fmt.Println("[ERROR] No Such File.") + return err + } + defer file.Close() + + outputFilePath := "outputs/" + GetFileNameWithoutExt(imageFile.fromFilepath) + ".jpg" + + img, _, err := image.Decode(file) + + dstfile, err := os.Create(outputFilePath) + if err != nil { + fmt.Println("[ERROR] No Such FilePath.") + return err + } + defer dstfile.Close() + + err = png.Encode(dstfile, img) + if err != nil { + fmt.Println("[ERROR] File Encode Failed.") + return err + } + + imageFile.fileExt = "jpg" + imageFile.toFilepath = outputFilePath + + return nil +} + +// GetFileNameWithoutExt returns the filename without file extension +func GetFileNameWithoutExt(path string) string { + return filepath.Base(path[:len(path)-len(filepath.Ext(path))]) +} diff --git a/kadai2/imgconvert/current_icon.png b/kadai2/imgconvert/current_icon.png new file mode 100644 index 0000000..4db6136 Binary files /dev/null and b/kadai2/imgconvert/current_icon.png differ diff --git a/kadai2/imgconvert/current_rena.jpg b/kadai2/imgconvert/current_rena.jpg new file mode 100644 index 0000000..8494899 Binary files /dev/null and b/kadai2/imgconvert/current_rena.jpg differ diff --git a/kadai2/imgconvert/godoc-converter.html b/kadai2/imgconvert/godoc-converter.html new file mode 100644 index 0000000..469e02a --- /dev/null +++ b/kadai2/imgconvert/godoc-converter.html @@ -0,0 +1,259 @@ + + + + + + + +
+ +func ConvertImagesFromJpgToPngInDir(dir string)+
+ConvertImagesFromJpgToPngInDir converts all jpg images to png in target directory. +
+ + + + + + + +func ConvertImagesFromPngToJpgInDir(dir string)+
+ConvertImagesFromPngToJpgInDir converts all png images to jpg in target directory. +
+ + + + + + + +func ConvertJpgToPng(imageFile *MyImageFile) error+
+ConvertJpgToPng convert target jpg image to png. +
+ + + + + + + +func ConvertPngToJpg(imageFile *MyImageFile) error+
+ConvertPngToJpg convert target png image to jpg. +
+ + + + + + + +func GetFileNameWithoutExt(path string) string+
+GetFileNameWithoutExt returns the filename without file extension +
+ + + + + + + +func GetFilepathListByExt(dir string, ext string) []string+
+GetFilepathListByExt returns the filepath list by the extention in target directory. +
+ + + + + + + + ++MyImageFile contains fileExt and filepath +
+ +type MyImageFile struct {
+ // contains filtered or unexported fields
+}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/kadai2/imgconvert/images/dir/sub_icon.png b/kadai2/imgconvert/images/dir/sub_icon.png
new file mode 100644
index 0000000..4db6136
Binary files /dev/null and b/kadai2/imgconvert/images/dir/sub_icon.png differ
diff --git a/kadai2/imgconvert/images/dir/sub_lena.jpg b/kadai2/imgconvert/images/dir/sub_lena.jpg
new file mode 100644
index 0000000..8494899
Binary files /dev/null and b/kadai2/imgconvert/images/dir/sub_lena.jpg differ
diff --git a/kadai2/imgconvert/images/icon.png b/kadai2/imgconvert/images/icon.png
new file mode 100644
index 0000000..4db6136
Binary files /dev/null and b/kadai2/imgconvert/images/icon.png differ
diff --git a/kadai2/imgconvert/images/lena.jpg b/kadai2/imgconvert/images/lena.jpg
new file mode 100644
index 0000000..8494899
Binary files /dev/null and b/kadai2/imgconvert/images/lena.jpg differ
diff --git a/kadai2/imgconvert/myconverter b/kadai2/imgconvert/myconverter
new file mode 100755
index 0000000..1468b1b
Binary files /dev/null and b/kadai2/imgconvert/myconverter differ
diff --git a/kadai2/imgconvert/myconverter.go b/kadai2/imgconvert/myconverter.go
new file mode 100644
index 0000000..8ab1b47
--- /dev/null
+++ b/kadai2/imgconvert/myconverter.go
@@ -0,0 +1,27 @@
+package main
+
+import (
+ "flag"
+ "fmt"
+
+ "./converter"
+)
+
+func main() {
+ var targetFilepath string
+ var fromFileExt string
+ var toFileExt string
+ flag.StringVar(&targetFilepath, "target", ".", "target filepath.")
+ flag.StringVar(&fromFileExt, "from", "jpg", "from file extention")
+ flag.StringVar(&toFileExt, "to", "png", "to file extention")
+ flag.Parse()
+
+ switch {
+ case fromFileExt == "jpg" && toFileExt == "png":
+ converter.ConvertImagesFromJpgToPngInDir(targetFilepath)
+ case fromFileExt == "png" && toFileExt == "jpg":
+ converter.ConvertImagesFromPngToJpgInDir(targetFilepath)
+ default:
+ fmt.Println("[ERROR]No supprot to convert from " + fromFileExt + " to " + toFileExt)
+ }
+}
diff --git a/kadai2/imgconvert/myconverter_test.go b/kadai2/imgconvert/myconverter_test.go
new file mode 100644
index 0000000..1d2b70f
--- /dev/null
+++ b/kadai2/imgconvert/myconverter_test.go
@@ -0,0 +1,25 @@
+package main
+
+import (
+ "testing"
+
+ "./converter"
+)
+
+func TestGetFileNameWithoutExt_OnlyFileName(t *testing.T) {
+ testdata := "file.png"
+ actual := converter.GetFileNameWithoutExt(testdata)
+ expected := "file"
+ if len(actual) != len(expected) {
+ t.Errorf("queue size is different. got %v but want %v", len(actual), len(expected))
+ }
+}
+
+func TestGetFileNameWithoutExt_WithFolderName(t *testing.T) {
+ testdata := "hoge/fuga/file.png"
+ actual := converter.GetFileNameWithoutExt(testdata)
+ expected := "file"
+ if len(actual) != len(expected) {
+ t.Errorf("queue size is different. got %v but want %v", len(actual), len(expected))
+ }
+}