二手空调回收go具体回收流程有谁知道,回收的钱怎么返还

9月1日融资榜:二手go来了 你的旧手机有救了_创投项目_中国创客网
京ICP备号-2 中国创客网 中国科技企业创客信息交互平台如何监控 golang 程序的垃圾回收
说明:本文测试环境 go version go1.6.2 darwin/amd64
本地开发环境的监控
如果是本地开发环境, 可以利用 GODEBUG=gctrace=1 /path/to/binary 的方式输出 GC 信息,然后用 gcvis 作可视化。
GODEBUG=gctrace=1 会输出如下格式的信息(输出到 stderr):
gc 1 @17.471s 0%: 0.22+4.4+0.19 ms clock, 0.66+0/1.8/10+0.57 ms cpu, 4-&4-&2 MB, 5 MB goal, 4 P
关于其资料,可以查阅: https://godoc.org/runtime ,这里引用下:
gctrace: setting gctrace=1 causes the garbage collector to emit a single line to standarderror at each collection, summarizing the amount of memory collected and thelength of the pause. Setting gctrace=2 emits the same summary but alsorepeats each collection. The format of this line is subject to change.Currently, it is:
gc # @#s #%: #+#+# ms clock, #+#/#/#+# ms cpu, #-&#-&# MB, # MB goal, # Pwhere the fields are as follows:
the GC number, incremented at each GC
time in seconds since program start
percentage of time spent in GC since program start
wall-clock/CPU times for the phases of the GC
#-&#-&# MB
heap size at GC start, at GC end, and live heap
goal heap size
number of processors usedThe phases are stop-the-world (STW) sweep termination, concurrentmark and scan, and STW mark termination. The CPU timesfor mark/scan are broken down in to assist time (GC performed inline with allocation), background GC time, and idle GC time.If the line ends with &(forced)&, this GC was forced by aruntime.GC() call and all phases are STW.
为了方便对应上字段,我简单标记了一下:
GODEBUG=gctrace=1 对应的实现在 src/runtime/mheap.go (go 1.6)
据说目前是每 两分钟 进行一次 GC forced, 关于其定义,我估计是下面这个,但是不太确定:
runtime/proc.go // forcegcperiod is the maximum time in nanoseconds between garbage // collections. If we go this long without a garbage collection, one // is forced to run. // // This is a variable for testing purposes. It normally doesn't change. var forcegcperiod int64 = 2 * 60 * 1e9
// 2 分钟 ... // check if we need to force a GC lastgc := int64(atomic.Load64(&memstats.last_gc)) if gcphase == _GCoff && lastgc != 0 && unixnow-lastgc & forcegcperiod && atomic.Load(&forcegc.idle) != 0 {
lock(&forcegc.lock)
forcegc.idle = 0
forcegc.g.schedlink = 0
injectglist(forcegc.g)
unlock(&forcegc.lock) }
从下图来看,还真是每两分钟一次 force GC 。
gcvis 的原理很简单, 就是逐行解析目标程序的 GC 输出,然后用正则匹配相关的数据,然后生成 JSON 数据,另外也会起一个协程开启 HTTP 服务,用于图表展示。
gcvis 主要有两种用法:
1、 直接运行
gcvis /path/to/binary
2、 管道重定向方式(standard error)
GODEBUG=gctrace=1
/path/to/binary
gcvis 的图标输出效果如下:
线上环境的监控
上面这种是不修改一行代码的情况下,完全使用外部工具/参数,无侵入式的 GC 监控。
另一种办法是直接读取 runtime.MemStats (runtime/mstats.go) 的内容。其实上面这种办法也是读取了 runtime.memstats (跟 runtime.MemStats 是同一个东西,一个对内,一个对外)。这也意味着要修改我们的程序代码。
我逛了一圈,发现不少人也是这么干的。
NSQ 对 GC 监控 /nsqio/nsq/blob/master/nsqd/statsd.go#L117
beego 对 GC 的监控: /astaxie/beego/blob/master/toolbox/profile.go#L96
Go port of Coda Hale’s Metrics library /rcrowley/go-metrics
A Golang library for exporting performance and runtime metrics to external metrics systems (i.e. statsite, statsd)
/armon/go-metrics/
总之,都是读取了 runtime.MemStats ,然后定时发往一些时序数据库之类的,然后展示。
代码基本都是这样:
memStats := &runtime.MemStats{}
runtime.ReadMemStats(memStats)
如果希望获取 gcstats:
gcstats := &debug.GCStats{PauseQuantiles: make([]time.Duration, 100)}
debug.ReadGCStats(gcstats)
如果你用了 open-falcon 作为监控工具的话,还可以用 /niean/goperfcounter , 配置一下即可使用。
&bases&: [“runtime”, “debug”], // 分别对应 runtime.MemStats, debug.GCStats }
如果读者看过 ReadMemStats 的实现的话,应该知道里面调用了 stopTheWorld 。 卧槽,这会不会出事啊!
Russ Cox 说,
We use ReadMemStats internally at Google. I am not sure of the period but it’s something like what you’re talking about (maybe up to once a minute, I forget).
Stopping the world i stopping the world for a long time is. ReadMemStats stops the world for only a fixed, very short amount of time. So calling it every 10-20 seconds should be fine.
Don’t take my word for it: measure how long it takes and decide whether you’re willing to give up that much of every 10-20 seconds. I expect it would be under 1/1000th of that time (10 ms) .
refer: /forum/#!searchin/golang-nuts/ReadMemStats/golang-nuts/mTnw5k4pZdo/rpK69Fns2MsJ
另外, /rcrowley/go-metrics 也提到了(go-metrics/runtime.go L:68)
runtime.ReadMemStats(&memStats) // This takes 50-200us .
我觉得一般业务,只要对性能没有很变态的要求,1毫秒内都还能接受吧,也看你读取的频率有多高。
由于每家公司使用的监控系统大相径庭,很难有大一统的解决办法,所以本文只是提供思路以及不严谨的考证。祝大家玩的开心!
基本都是围绕 runtime.MemStats 做文章;
没事多看看 runtime 代码,加深理解。
最新教程周点击榜
微信扫一扫Go语言作为一个现代化的编程语言以及支持垃圾内存的自动回收特性(GC).
我们现在关注的是非内存资源的自动回收技术.
## 局部资源的管理
在讨论Go语言解决方案之前, 我们先看看C++是怎么管理资源的.
C++中可以可以自动执行的代码主要是构造函数和析构函数.
因此, 很多资源的管理技术都是基于构造函数和析构函数实现.
比较常见的是C++的RAII(Resource Acquisition Is Initialization)技术,
即初始化中获取资源. 比如在多线程编程中用到的`MutexLocker`:
struct MutexLock {
Mutex *const mu_;
MutexLock(Mutex *mu): mu_(mu)
mu_-&Lock();
~MutexLock() {
mu_-&Unlock();
这样在使用`Mutex`的时候就不会忘记解锁的操作了:
void* safeRead(Mutex *mu) {
MutexLock locker(mu);
return NULL;
return read();
其实RAII中最重要的是退出`locker`作用域是自动执行对象的析构函数,
这里也就是`mu_-&Unlock();`语句.
C++的构造函数其实是次要的. 关于禁用C++构造函数的讨论可以参考我的
另一个文章: [C++去掉构造函数会怎么样?](http://my.oschina.net/chai2010/blog/118105)
因为构造函数经常是通过显示定义变量而隐式调用的, 因此用普通的全局函数也
可以实现构造函数的功能(唯一的约束是值容器).
其实C语言的`fopen`就是一个`FILE`对象的构造函数.
而作为C语言简约哲学继承者的Go语言同样也没有对构造函数做特殊处理.
在Go语言中构造函数这是约定以`New`开头的普通函数, 比如`NewBuffer`.
Go语言/UNIX之父`Ken Thompson`发明了`defer`语句, 完美地
解决了析构函数的问题(`defer`还有很多其他特性).
因此, 在释放局部资源时, 可以用`defer`管理. 因为C++的RAII的构造
函数和析构函数耦合过于紧密, 对于资源申请失败的问题就比较麻烦.
但是Go语言的`defer`则灵活很多.
比如, Go语言版本基于`defer`的`Mutex`用法
func safeRead(Mutex *mu) []byte {
defer mu.Unlock()
return read();
对于可能申请失败的资源也很好处理:
func loadFile(name string) ([]byte, error) {
f, err := os.Open(name)
if err != nil {
return nil, err
defer f.Close()
return load(f)
使用`defer`语句, 可以方便地组合函数/闭包和资源对象.
即使`panic`时, `defer`也能保证资源的正确释放.
## 非局部资源的管理
我们之前看到的都是在局部使用和释放资源.
如果资源的生命周期很长, 而且可能被多个模块共享和随意传递的话,
`defer`语句就不好处理了.
解决的思路和C++的RAII的方式类似: 我们需要一个能够自己定义的类似
析构函数的技术.
但是因为Go语言有GC特性, 因此没有析构函数的概念. 不过`runtime`包的
`func SetFinalizer(x, f interface{})`函数可以提供类似的机制.
比如, 我们可以包装一个文件对象, 在没有人使用的时候能够自动关闭:
type MyFile struct {
f *os.File
func NewFile(name string) (*MyFile, error) {
f, err := os.Open(name)
if err != nil {
return nil, err
runtime.SetFinalizer(f, f.Close)
return &MyFile{f:f}, nil
func (f *MyFile) Close() {
f.f.Close()
在使用`runtime.SetFinalizer`时, 需要注意的地方是尽量要用指针访问
内部资源. 这样的话, 即使`*MyFile`对象忘记释放, 或者是被别的对象无意中覆盖,
也可以保证内部的文件资源可以正确释放.
Go语言是短小精悍的语言, 它的设计哲学来自UNIX和C语言的KISS原则.
但是Go语言的语法规范虽然很少(50+页), 但是却提供了无限可能的组合方式.
Go语言之父`Rob Pike`有篇文章叫 [少是指数级的多](/2012/06/%E7%BF%BB%E8%AF%91%E5%B0%91%E6%98%AF%E6%8C%87%E6%95%B0%E7%BA%A7%E7%9A%84%E5%A4%9A/). 但是为什么少就是多呢?
参考下数学公理就明白了: 数学的基础规则是很简单的, 但是组合方式却是无穷的.
Go语言的思路也是提供虽然少但却是正交的基础特性, 通过不同特性的无穷的
组合方式来应对各种问题(一个反例就是C++的构造函数和析构函数).
这里我们主要是基于Go语言的`defer`和`runtime.SetFinalizer`两个基础特性,
来解决资源的自动回收问题.
& 开源中国(OSChina.NET) |
开源中国社区(OSChina.net)是工信部
指定的官方社区}

我要回帖

更多关于 二手房契税返还 的文章

更多推荐

版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。

点击添加站长微信