zoukankan      html  css  js  c++  java
  • Purity in My Programming: Functions in Go

    原文连接

    https://hackernoon.com/purity-in-my-programming-pure-functions-in-go-c21m3u2z

    什么是纯函数

    在程序设计中,若一个函数符合以下要求,则它可能被认为是纯函数: 此函數在相同的输入值時,需產生相同的輸出。 函數的輸出和輸入值以外的其他隐藏信息或狀態無關,也和由I/O設備產生的外部輸出無關。 该函数不能有语义上可观察的函数副作用,诸如“触发事件”,使輸出設備輸出,或更改輸出值以外物件的內容等。(wiki)

    如何理解

    纯函数的好处和坏处都有,坏处就是容易产生大量的参数列表,好处就是快,稳定,准确。当然,还是要使用起来的。

    例子

    这里示例一步步改进

    step1

    totalCounted := map[string]int{}
    
    func countNamesInText(text string) {
    	total := 0
    	const name = getNameFromDatabase()
    	for _, word := range strings.Split(text, " ") {
    		if word == mention {
    			total++
    		}
    	}
    	totalCounted[name] = total
    }
    

    这句显然违法了纯函数的基本定义,对一个全局的变量state changed

    	totalCounted[name] = total
    

    step2

    func countNamesInText(text string) int {
    	totalCounted := 0
    	const name = getNameFromDatabase()
    	for _, word := range strings.Split(text, " ") {
    		if word == mention {
    			totalCounted++
    		}
    	}
    	return totalCounted
    }
    

    似乎看起来ok,但是还有一个痛点,数据库的读取

    const name = getNameFromDatabase()
    

    这就取决于数据库是否配置开启,是否中途数据篡改等,举一个这种情况下的“糟糕”的测试

    func TestCountNamesInText(t *testing.T) {
    	assert.Equal(t, 2, countNamesInText("this word here"))
    }
    

    其实这个并不是测试的锅,但是这的确会导致test failed

    step3

    func countNamesInText(text, name string) int {
    	totalCounted := 0
    	for _, word := range strings.Split(text, " ") {
    		if word == mention {
    			totalCounted++
    		}
    	}
    	return totalCounted
    }
    
    func TestCountNamesInText(t *testing.T) {
    	assert.Equal(t, 1, countNamesInText("this word here", "this"))
    }
    

    似乎没什么问题了,ok,的确没问题了

    end

    这种函数怎么顺序使用呢

    totalCounted := map[string]int{}
    name := getNameFromDatabase()
    totalCounted[name] = countNamesInText("some name in here", name)
    

    可以看到我们需要提前对参数在func外部获取,如果参数过多,则会陷入“参数列表”的窘境,pure or impure都没错,看人的水平能否把控。

  • 相关阅读:
    (一)jQuery EasyUI 的EasyLoader载入原理
    java playframework
    android Handlerr.removeCallbacksAndMessages(null)的妙用
    云已成为一种趋势,大有可为
    将一个4X4的数组进行逆时针旋转90度后输出,要求原数组数据随机输入
    小强的HTML5移动开发之路(40)——jqMobi中实践header定义的几种方式
    AngularJS中的依赖注入
    极光消息推送服务器端开发实现推送(下)
    用CSS指定外部链接的样式
    版本控制(1)——SVN
  • 原文地址:https://www.cnblogs.com/CherryTab/p/13226947.html
Copyright © 2011-2022 走看看