<music>

  |------<src>

       |-------<library>

            |-------manager.go

            |-------manager_test.go

       |-------<play>

            |-------play.go

            |-------mp3.go

            |-------wav.go

       |--------<music>

            |-------mplayer.go

  |------<pkg>

  |------<bin>

------------------------------------------------------------------------------------

library:音乐库文件所在目录

[manager.go]

 package  library

 import "errors"

 type MusicEntry struct {
Id string
Name string
Artist string
Source string
Type string
} type MusicManager struct {
musics []MusicEntry
} func NewMusicManager() *MusicManager {
return &MusicManager{make([]MusicEntry, )}
} func (m *MusicManager) Len() int {
return len(m.musics)
} func (m *MusicManager) Get(index int) (music *MusicEntry, err error) {
if index < || index >= len(m.musics) {
return nil, errors.New("Index out of range.")
}
return &m.musics[index], nil
} func (m *MusicManager) Find(name string) *MusicEntry {
if len(m.musics)== {
return nil
} for _,mm := range m.musics {
if mm.Name == name {
return &mm
}
}
return nil
} func (m *MusicManager)Add(music *MusicEntry) {
m.musics = append(m.musics, *music)
} func (m *MusicManager)Remove(index int) *MusicEntry {
if index< || index >= len(m.musics) {
return nil
} removedMusic := &m.musics[index] if index < len(m.musics)- {
m.musics = append(m.musics[:index-], m.musics[index+:]...)
} else if index == {
m.musics = make([]MusicEntry, )
}else {
m.musics = m.musics[:index-]
}
return removedMusic
}

[manager_test.go]

 package library

 import (
"testing"
) func TestOps(t *testing.T) {
mm := NewMusicManager()
if mm == nil {
t.Error("NewMusicManager() failed.")
}
m0 := &MusicEntry {"", "Cellion Dion", "My Heart Will Go On", "http://qbox.me/24501234", "MP3" }
mm.Add(m0) if mm.Len() != {
t.Error("MusicManager.Add() failed.")
} m := mm.Find(m0.Name) if m == nil {
t.Error("MusicManager.Find() failed.")
} if m.Id != m0.Id || m.Artist != m0.Artist || m.Name != m0.Name || m.Source != m0.Source || m.Type != m0.Type {
t.Error("MusicManager.Find() failed. Found item mismatch.")
} m, err := mm.Get() if m == nil {
t.Error("MusicManager.Get() failed.", err)
} m = mm.Remove()
if m == nil || mm.Len() != {
t.Error("MusicManager.Remove() failed.", err)
}
}

play:各种音乐类型存放库

[play.go]

 package play

 import "fmt"

 type Player interface {
Play(source string)
} func Play(source, mtype string) {
var p Player
switch mtype {
case "MP3":
p = &MP3Player{}
case "WAV":
p = &WAVPlayer{}
default:
fmt.Println("Unsupported music type", mtype)
return
}
p.Play(source)
}

[mp3.go]

 package play

 import (
"fmt"
"time"
) type MP3Player struct {
stat int
progress int
} func (p *MP3Player)Play(source string) {
fmt.Println("Playing MP3 music", source) p.progress = for p.progress < {
time.Sleep(*time.Millisecond)
fmt.Print(".")
p.progress +=
} fmt.Println("\nFinished playing", source)
}

[wav.go]

 package play

 import (
"fmt"
"time"
) type WAVPlayer struct {
stat int
progress int
} func (p *WAVPlayer) Play(source string) {
fmt.Println("Playing WAV music", source) p.progress = for p.progress < {
time.Sleep(*time.Millisecond)
fmt.Print(".")
p.progress +=
} fmt.Println("\nFinished playing", source)
}

music:主程序的放在处

[mplayer.go]

 package main

 import  (
"bufio"
"fmt"
"os"
"strconv"
"strings"
"play"
"library"
) var lib *library.MusicManager
var id int =
var ctrl, signal chan int func handleLibCommands(tokens []string) {
switch tokens[] {
case "list" :
for i:=; i<lib.Len(); i++ {
e,_ := lib.Get(i)
fmt.Println(i+, ":", e.Name, e.Artist, e.Source, e.Type)
}
case "add":
if len(tokens) == {
id++
lib.Add(&library.MusicEntry{string(strconv.Itoa(id)),tokens[],tokens[],tokens[],tokens[]})
}else {
fmt.Println("USAGE: library add <name><artist><source><type>")
}
case "remove":
if len(tokens) == {
lib.Remove() // 有问题
} else {
fmt.Println("USAGE: library remove <name>")
}
default:
fmt.Println("Unrecongnized library command:", tokens[])
}
} func handlePlayCommands(tokens []string) {
if len(tokens) != {
fmt.Println("USAGE: play <name>")
return
} e := lib.Find(tokens[]) if e == nil {
fmt.Println("The music", tokens[], "does not exist.")
return
} play.Play(e.Source, e.Type)
} func main() {
fmt.Println(`
Enter following commands to control the player:
lib add <name><artist><source><type>
lib remove <name>
play <name>
`) lib = library.NewMusicManager() r := bufio.NewReader(os.Stdin) for {
fmt.Println("Enter command->") rawLine,_,_ := r.ReadLine() line := string(rawLine) if line == "q" || line == "e" {
break
} tokens := strings.Split(line, " ") if tokens[] == "lib" {
handleLibCommands(tokens)
}else if tokens[] == "play" {
handlePlayCommands(tokens)
}else {
fmt.Println("Unrecongnized command:", tokens[])
}
}
}

;之后,返回到music目录节点,执行如下命令:

go build library

go build play

go build music

go test library

go install library

go install play

go install music

--------------------------------------------------------------------

接口使用的感受:

  1、类似于C++中虚基类的作用,作为一个消费者的接口,用于接收生产者设计的方法;

  2、生产者设计也简单,只需要实现接口中的方法就算设计了接口【无需如C++的,还需要继承】;

  3、使用简单,设计也简单;

GO语言(六)接口使用的更多相关文章

  1. R语言数据接口

    R语言数据接口 R语言处理的数据一般从外部导入,因此需要数据接口来读取各种格式化的数据 CSV # 获得data是一个数据帧 data = read.csv("input.csv" ...

  2. [日常] Go语言圣经--接口约定习题

    Go语言圣经-接口1.接口类型是对其它类型行为的抽象和概括2.Go语言中接口类型的独特之处在于它是满足隐式实现的3.Go语言中还存在着另外一种类型:接口类型.接口类型是一种抽象的类型4.一个类型可以自 ...

  3. FFI (语言交互接口(Foreign Function Interface))

    FFI(Foreign Function Interface)是用来与其它语言交互的接口, 在有些语言里面称为语言绑定(language bindings), Java 里面一般称为 JNI(Java ...

  4. python语言(六)mock接口开发、发邮件、写日志、新Excel操作

    一.urllib模块 urllib模块是一个标准模块,直接import urllib即可,在python3里面只有urllib模块,在python2里面有urllib模块和urllib2模块. url ...

  5. C语言原子接口与实现

    原子是一个指向唯一的.不可变的0个或任意多个字节序列的指针,大多数原子都是指向以空字符结束的字符串,但是任何一个指向任意字节序列的指针都可以使原子.任何原子只能出现一次.如果两个原子指向同一个内存单元 ...

  6. c语言调试接口

    http://blog.chinaunix.net/uid-10106787-id-2985587.html 在C语言程序设计中,常会出现各种各样的bug:段错误.参数异常等等.我们需要尽快定位错误, ...

  7. Java语言Socket接口用法详解

    Socket接口用法详解   在Java中,基于TCP协议实现网络通信的类有两个,在客户端的Socket类和在服务器端的ServerSocket类,ServerSocket类的功能是建立一个Serve ...

  8. Go语言的接口

    一.接口的定义和好处 我们都知道接口给类提供了一种多态的机制,什么是多态,多态就是系统根据类型的具体实现完成不同的行为. 以下代码简单说明了接口的作用 package main import ( &q ...

  9. go语言学习-接口

    Go语言中虽然没有传统面向对象语言中类.集成的概念,不过提供了接口的支持,可以使用接口来使用一些面向对象的特性. 在 go 语言中,的接口有下面几个特点: 可以包含0个或多个方法的签名 只定义方法的签 ...

  10. Go语言的接口interface、struct和组合、继承

    Go语言的interface概念相对于C++中的基类,通过interface来实现多态功能. 在C++中,当需要实现多态功能时,步骤是首先定义一个基类,该基类使用虚函数或者纯虚函数抽象了所有子类会用到 ...

随机推荐

  1. target与currentTarget区别

    target在事件流的目标阶段:currentTarget在事件流的捕获,目标及冒泡阶段.只有当事件流处在目标阶段的时候,两个的指向才是一样的, 而当处于捕获和冒泡阶段的时候,target指向被单击的 ...

  2. 我java学习时的模样(二)

    去掉自己浮躁的心 工作了三年,见识过高山,也见过低估,高山同大神一起共事,低估是几家特别烂的外包公司,现在有了另一种心境.已经开始重视自己,去掉当初浮躁的心. 毕业的一两年内,是人成长特别快的时期,也 ...

  3. 巧用hover改变css样式和背景

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  4. 【Bigdecimal】

    ---恢复内容开始--- 大位数除法的时候注意1/3问题:异常:[Exception in thread "main" java.lang.ArithmeticException: ...

  5. 记录日志好习惯——Log4net入门(WCF篇)

    本篇是在学习了“编码之道”的Log4net入门(WCF篇)http://www.cnblogs.com/yonghuacui/p/6181864.html之后,总结了一些自认为比较重要的细节.顺便把创 ...

  6. C# 多线程系列之Semaphore使用

    Semaphore,即信号量的意思.是操作系统原始提供的内核同步对象. Semaphore semaphoreAcceptedClients = , 3,"Semaphore1") ...

  7. 在 Azure 上创建和链接 Azure SQL 数据库

    本快速入门介绍了如何在 Azure 门户中创建并连接 Azure SQL 数据库.在本教程中完成的所有操作均符合 1 元试用条件. 开始之前 如果您还没有 Azure 账户,可以申请 1 元试用账户. ...

  8. 数据结构--ADT

    好吧,这个没什么好讲的,写过java代码的人估计一直都在用ADT, ADT,其实就是abstract data type,抽象数据类型,额,其实他丫就是,java 的class...... 不过关于A ...

  9. SpringCloud实战之初级入门(三)— spring cloud config搭建git配置中心

    目录 1.环境介绍 2.配置中心 2.1 创建工程 2.2 修改配置文件 2.3 在github中加入配置文件 2.3 修改启动文件 3. 访问配置中心 1.环境介绍 上一篇文章中,我们介绍了如何利用 ...

  10. Java Native Interface Specification Contents 翻译

    https://docs.oracle.com/en/java/javase/12/docs/specs/jni/index.html Google翻译 第1章:简介 本章介绍Java Native ...