首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何使用Go编程语言读取彩色的png文件并输出为灰度?

如何使用Go编程语言读取彩色的png文件并输出为灰度?
EN

Stack Overflow用户
提问于 2012-01-02 11:07:00
回答 5查看 14.8K关注 0票数 10

如何在Go编程语言中读取彩色.png文件,并将其输出为8位灰度图像?

EN

回答 5

Stack Overflow用户

发布于 2012-01-02 11:30:11

下面的程序接受一个输入文件名和一个输出文件名。它打开输入文件,对其解码,将其转换为灰度,然后将其编码为输出文件。

此程序不是特定于PNG的,但要支持其他文件格式,您必须导入正确的图像包。例如,要添加JPEG支持,可以将其添加到导入列表_ "image/jpeg"

如果你只想支持PNG,那么你可以直接使用image/png.Decode而不是image.Decode

代码语言:javascript
复制
package main

import (
    "image"
    "image/png" // register the PNG format with the image package
    "os"
)

func main() {
    infile, err := os.Open(os.Args[1])
    if err != nil {
        // replace this with real error handling
        panic(err.String())
    }
    defer infile.Close()

    // Decode will figure out what type of image is in the file on its own.
    // We just have to be sure all the image packages we want are imported.
    src, _, err := image.Decode(infile)
    if err != nil {
        // replace this with real error handling
        panic(err.String())
    }

    // Create a new grayscale image
    bounds := src.Bounds()
    w, h := bounds.Max.X, bounds.Max.Y
    gray := image.NewGray(w, h)
    for x := 0; x < w; x++ {
        for y := 0; y < h; y++ {
            oldColor := src.At(x, y)
            grayColor := image.GrayColorModel.Convert(oldColor)
            gray.Set(x, y, grayColor)
        }
    }

    // Encode the grayscale image to the output file
    outfile, err := os.Create(os.Args[2])
    if err != nil {
        // replace this with real error handling
        panic(err.String())
    }
    defer outfile.Close()
    png.Encode(outfile, gray)
}
票数 14
EN

Stack Overflow用户

发布于 2013-06-13 06:22:41

我自己也遇到了这个问题,并提出了一个略有不同的解决方案。我引入了一个实现image.Image的新类型ConvertedConverted由原始图像和color.Model组成。

Converted在每次被访问时都会进行转换,这可能会带来稍差的性能,但从另一方面来说,它很酷,而且是可组合的。

代码语言:javascript
复制
package main

import (
    "image"
    _ "image/jpeg" // Register JPEG format
    "image/png"    // Register PNG  format
    "image/color"
    "log"
    "os"
)

// Converted implements image.Image, so you can
// pretend that it is the converted image.
type Converted struct {
    Img image.Image
    Mod color.Model
}

// We return the new color model...
func (c *Converted) ColorModel() color.Model{
    return c.Mod
}

// ... but the original bounds
func (c *Converted) Bounds() image.Rectangle{
    return c.Img.Bounds()
}

// At forwards the call to the original image and
// then asks the color model to convert it.
func (c *Converted) At(x, y int) color.Color{
    return c.Mod.Convert(c.Img.At(x,y))
}

func main() {
    if len(os.Args) != 3 { log.Fatalln("Needs two arguments")}
    infile, err := os.Open(os.Args[1])
    if err != nil {
        log.Fatalln(err)
    }
    defer infile.Close()

    img, _, err := image.Decode(infile)
    if err != nil {
        log.Fatalln(err)
    }

    // Since Converted implements image, this is now a grayscale image
    gr := &Converted{img, color.GrayModel}
    // Or do something like this to convert it into a black and
    // white image.
    // bw := []color.Color{color.Black,color.White}
    // gr := &Converted{img, color.Palette(bw)}


    outfile, err := os.Create(os.Args[2])
    if err != nil {
        log.Fatalln(err)
    }
    defer outfile.Close()

    png.Encode(outfile,gr)
}
票数 10
EN

Stack Overflow用户

发布于 2014-11-17 21:58:03

@EvanShaw的代码片段现在不能工作了,(可能是一些golang API发生了变化)我将其改编如下。遗憾的是,它输出了一个灰度图像,但内容混乱,目前我不知道为什么。我在这里提供给你参考。

代码语言:javascript
复制
    package main

    import (
        "image"
        "image/color"
        "image/png"
        "math"
        "os"
    )

    func main() {
        filename := "dir/to/myfile/somefile.png"
        infile, err := os.Open(filename)
        if err != nil {
            // replace this with real error handling
            panic(err.Error())
        }
        defer infile.Close()

        // Decode will figure out what type of image is in the file on its own.
        // We just have to be sure all the image packages we want are imported.
        src, _, err := image.Decode(infile)
        if err != nil {
            // replace this with real error handling
            panic(err.Error())
        }

        // Create a new grayscale image
        bounds := src.Bounds()
        w, h := bounds.Max.X, bounds.Max.Y
        gray := image.NewGray(image.Rectangle{image.Point{0, 0}, image.Point{w, h}})
        for x := 0; x < w; x++ {
            for y := 0; y < h; y++ {
                oldColor := src.At(x, y)
                r, g, b, _ := oldColor.RGBA()
                avg := 0.2125*float64(r) + 0.7154*float64(g) + 0.0721*float64(b)
                grayColor := color.Gray{uint8(math.Ceil(avg))}
                gray.Set(x, y, grayColor)
            }
        }

        // Encode the grayscale image to the output file
        outfilename := "result.png"
        outfile, err := os.Create(outfilename)
        if err != nil {
            // replace this with real error handling
            panic(err.Error())
        }
        defer outfile.Close()
        png.Encode(outfile, gray)
    }

顺便说一下,golang不能自动解码图像文件,我们需要直接使用图像类型的Decode方法。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/8697095

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档