package main
import (
"os"
"io"
"fmt"
)
func main() {
for {
buffer := make([]byte, 5)
size, err := os.Stdin.Read(buffer)
if err == io.EOF {
fmt.Println("EOF")
break
}
fmt.Printf("size=%d input='%s'\n", size, string(buffer))
}
}
package main
import (
"os"
"io"
)
func main() {
file, err := os.Open("main.go")
if err != nil {
panic(err)
}
defer file.Close()
io.Copy(os.Stdout, file)
}
package main
import (
"net"
"net/http"
"bufio"
"fmt"
"io"
"os"
)
func main() {
conn, err := net.Dial("tcp", "ascii.jp:80")
if err != nil {
panic(err)
}
conn.Write([]byte("GET / HTTP/1.0\r\nHost: ascii.jp\r\n\r\n"))
res, err := http.ReadResponse(bufio.NewReader(conn), nil)
fmt.Println(res.Header)
defer res.Body.Close()
io.Copy(os.Stdout, res.Body)
}
package main
import (
"bytes"
"encoding/binary"
"fmt"
)
func main() {
data := []byte{0x0, 0x0, 0x27, 0x10}
var i int32
binary.Read(bytes.NewReader(data), binary.BigEndian, &i)
fmt.Printf("data: %d\n", i)
}
package main
import (
"io"
"encoding/binary"
"fmt"
"os"
)
func dumpChunk(chunk io.Reader) {
var length int32
binary.Read(chunk, binary.BigEndian, &length)
buffer := make([]byte, 4)
chunk.Read(buffer)
fmt.Printf("chunk, '%v' (%d bytes)\n", string(buffer), length)
}
func readChunks(file *os.File) []io.Reader {
var chunks []io.Reader
file.Seek(8, 0)
var offset int64 = 8
for {
var length int32
err := binary.Read(file, binary.BigEndian, &length)
if err == io.EOF {
break
}
chunks = append(chunks, io.NewSectionReader(file, offset, int64(length)+12))
offset, _ = file.Seek(int64(length+8), 1)
}
return chunks
}
func main() {
file, err := os.Open("Lenna.png")
if err != nil {
panic(err)
}
defer file.Close()
chunks := readChunks(file)
for _, chunk := range chunks {
dumpChunk(chunk)
}
}
実行結果
chunk, 'IHDR' (13 bytes)
chunk, 'sRGB' (1 bytes)
chunk, 'IDAT' (473761 bytes)
chunk, 'IEND' (0 bytes)
Process finished with exit code 0
package main
import (
"io"
"bytes"
"encoding/binary"
"hash/crc32"
"os"
"fmt"
)
func textChunk(text string) io.Reader {
byteData := []byte(text)
var buffer bytes.Buffer
binary.Write(&buffer, binary.BigEndian, int32(len(byteData)))
buffer.WriteString("tExt")
buffer.Write(byteData)
crc := crc32.NewIEEE()
io.WriteString(crc, "tExt")
binary.Write(&buffer, binary.BigEndian, crc.Sum32())
return &buffer
}
func readChunks(file *os.File) []io.Reader {
var chunks []io.Reader
file.Seek(8, 0)
var offset int64 = 8
for {
var length int32
err := binary.Read(file, binary.BigEndian, &length)
if err != nil {
break
}
chunks = append(chunks, io.NewSectionReader(file, offset, int64(length)+12))
offset , _ = file.Seek(int64(length+8), 1)
}
return chunks
}
func dumpChunk(chunk io.Reader) {
var length int32
binary.Read(chunk, binary.BigEndian, &length)
buffer := make([]byte, 4)
chunk.Read(buffer)
fmt.Printf("chunk '%v' (%d bytes\n", string(buffer), length)
if bytes.Equal(buffer, []byte("tExt")) {
rawText := make([]byte, length)
chunk.Read(rawText)
fmt.Println(string(rawText))
}
}
func writeFile() {
file, err := os.Open("Lenna.png")
if err != nil {
panic(err)
}
defer file.Close()
newFile, err := os.Create("Lenna2.png")
if err != nil {
panic(err)
}
chunks := readChunks(file)
io.WriteString(newFile, "\x89PNG\r\n\x1a\n")
io.Copy(newFile, chunks[0])
io.Copy(newFile, textChunk("ASCII PROGRAMMING++"))
for _, chunk := range chunks[1:] {
io.Copy(newFile, chunk)
}
}
func readFile() {
file, err := os.Open("Lenna2.png")
if err != nil {
panic(err)
}
defer file.Close()
chunks := readChunks(file)
for _, chunk := range chunks {
dumpChunk(chunk)
}
}
func main() {
writeFile()
readFile()
}
package main
import (
"bufio"
"strings"
"fmt"
"io"
)
var source = `1行目
2行目
3行目`
func main() {
reader :=bufio.NewReader(strings.NewReader(source))
for {
line, err := reader.ReadString('\n')
fmt.Printf("%#v\n", line)
if err == io.EOF {
break
}
}
}
package main
import (
"bufio"
"strings"
"fmt"
)
var source = `1行目
2行目
3行目`
func main() {
scanner := bufio.NewScanner(strings.NewReader(source))
for scanner.Scan() {
fmt.Printf("%#v\n", scanner.Text())
}
}
package main
import (
"strings"
"fmt"
)
var source = "123 1.234 1.0e4 test"
func main() {
reader := strings.NewReader(source)
var i int
var f, g float64
var s string
fmt.Fscan(reader, &i, &f, &g, &s)
fmt.Printf("i=%#v f=%#v g=%#v s=%#v\n", i, f, g, s)
}
実行結果
i=123 f=1.234 g=10000 s="test"
Fscan
はスペース(または改行)で区切られたstringを読み込んで2つ目以降の引数の変数に代入していく。
package main
import (
"strings"
"encoding/csv"
"io"
"fmt"
)
var csvSource =
`13101, "100 ", "1000003", "トウキョウト", "チヨダク", "ヒトツバシ(1チョウメ)", "東京都", "千代田区", "一ツ橋(1丁目)", 1,0,1,0,0,0
13101, "101 ", "1000003", "トウキョウト", "チヨダク", "ヒトツバシ(2チョウメ)", "東京都", "千代田区", "一ツ橋(2丁目)", 1,0,1,0,0,0
13101, "100 ", "1000012", "トウキョウト", "チヨダク", "ヒビヤコウエン", "東京都", "千代田区", "日比谷公園", 0,0,0,0,0,0
13101, "102 ", "1000093", "トウキョウト", "チヨダク", "ヒトツバシ(1チョウメ)", "東京都", "千代田区", "平河町", 0,0,1,0,0,0
13101, "102 ", "1000071", "トウキョウト", "チヨダク", "ヒトツバシ(1チョウメ)", "東京都", "千代田区", "富士見", 0,0,1,0,0,0
`
func main() {
reader := strings.NewReader(csvSource)
csvReader := csv.NewReader(reader)
csvReader.LazyQuotes = true
for {
line, err := csvReader.Read()
if err == io.EOF {
break
}
fmt.Println(line[2], line[6:9])
}
}
実行結果
"1000003" [ "東京都" "千代田区" "一ツ橋(1丁目)"]
"1000003" [ "東京都" "千代田区" "一ツ橋(2丁目)"]
"1000012" [ "東京都" "千代田区" "日比谷公園"]
"1000093" [ "東京都" "千代田区" "平河町"]
"1000071" [ "東京都" "千代田区" "富士見"]
BOM付UTF-8にはまった。書籍そのままでは動かない。
GoでBOM付きのUTF8なCSVを扱うには | tail -f pinzo.log
encoding/csv: bare " in non-quoted-field · Issue #21672 · golang/go · GitHub
- io.Reader/io.Writerでストリームを自由に操る
package main
import (
"bytes"
"io"
"os"
)
func main() {
header := bytes.NewBufferString(("----- HEADER -----\n"))
content := bytes.NewBufferString("Example of io.MultiReader\n")
footer := bytes.NewBufferString("----- FOOTER -----\n")
reader := io.MultiReader(header, content, footer)
io.Copy(os.Stdout, reader)
}
package main
import (
"bytes"
"fmt"
"io"
"io/ioutil"
)
func main() {
var buffer bytes.Buffer
reader := bytes.NewBufferString("Example of io.TeeReader\n")
teeReader := io.TeeReader(reader, &buffer)
_, _ = ioutil.ReadAll(teeReader)
fmt.Println(buffer.String())
}