doumi1884 2018-07-12 09:49
浏览 115

为什么Bild中的jpeg.Decode(bytes.NewReader(imageBytes))和jpeg.Encode(buf,img,nil)占用大量CPU?

I am trying to build an application which manipulates images on the run using Bild. But the above-mentioned methods are eating up a lot CPU(90%) for images. What is the reason for these methods to use high CPU? Are there any other methods or packages which uses less CPU?

func imageDecode(imageBytes []byte) (image.Image, error) {
    contentType := http.DetectContentType(imageBytes)
    var err error
    var img image.Image
    if contentType == constants.PngContentType {
        img, err = png.Decode(bytes.NewReader(imageBytes))
    } else if contentType == constants.JpegContentType {
        img, err = jpeg.Decode(bytes.NewReader(imageBytes))
    } else if contentType == constants.GifContentType {
        img, err = gif.Decode(bytes.NewReader(imageBytes))
    } else {
        img, err = nil, fmt.Errorf("decode error invalid content-type for filename: ")
    }
    if err != nil {
        return img, err
    }
    return img, nil
}

func imageEncode(imageBytes []byte, img image.Image) ([]byte, error) {
    contentType := http.DetectContentType(imageBytes)
    if contentType == constants.PngContentType && isOpaque(img) {
        contentType = constants.JpegContentType
    }
    buf := new(bytes.Buffer)
    var err error
    var transformedImageBytes []byte
    if contentType == constants.PngContentType {
        pngEnc := png.Encoder{CompressionLevel: png.BestCompression}
        err = pngEnc.Encode(buf, img)
    } else if contentType == constants.JpegContentType {
        err = jpeg.Encode(buf, img, nil)
    } else if contentType == constants.GifContentType {
        err = gif.Encode(buf, img, nil)
    } else {
        err = fmt.Errorf("encode error invalid content-type")
    }
    if err != nil {
        return transformedImageBytes, err
    }
    transformedImageBytes = buf.Bytes()
    return transformedImageBytes, err
}
  • 写回答

1条回答 默认 最新

  • dtwvr26066 2018-07-12 10:29
    关注

    You don't need to manually detect the image type and use different decoding calls, the image package does that for you already, when using image.Decode(). Just make sure you have the image decoders registered prior, which you can achieve by using blank imports, e.g.:

    import (
        _ "image/gif"
        _ "image/jpeg"
        _ "image/png"
    )
    
    func imageDecode(imageBytes []byte) (image.Image, error) {
        img, _, err := image.Decode(bytes.NewReader(imageBytes))
    }
    

    Although I'm not sure performance will improve significantly by this.

    What you should do is use "smart" conversion. By this I mean in certain cases you can omit decoding and re-encoding the image, you can just send the input to the output as-is (e.g. using io.Copy()):

    • If input is a GIF image.
    • If input is a JPEG image.

    You only have to truly decode the image if it is of PNG format. Note that detecting if a PNG image is opaque is slow as it has to examine all the pixels (unless a transparent pixel is found earlier).

    评论

报告相同问题?

悬赏问题

  • ¥15 关于#matlab#的问题:在模糊控制器中选出线路信息,在simulink中根据线路信息生成速度时间目标曲线(初速度为20m/s,15秒后减为0的速度时间图像)我想问线路信息是什么
  • ¥15 banner广告展示设置多少时间不怎么会消耗用户价值
  • ¥16 mybatis的代理对象无法通过@Autowired装填
  • ¥15 可见光定位matlab仿真
  • ¥15 arduino 四自由度机械臂
  • ¥15 wordpress 产品图片 GIF 没法显示
  • ¥15 求三国群英传pl国战时间的修改方法
  • ¥15 matlab代码代写,需写出详细代码,代价私
  • ¥15 ROS系统搭建请教(跨境电商用途)
  • ¥15 AIC3204的示例代码有吗,想用AIC3204测量血氧,找不到相关的代码。