前言:

  在上一篇讲解了基于glib实现抽象和继承后,当然这篇就得讲讲接口类型啦!

  在JAVA中接口更多的弥补了其单继承所带来的缺陷,使其能够扩展很多功能,同时又不破坏它的结构。其实接口就是一种协议,在A类不能直接调用B类方法、尽量降低耦合性和避免杂糅混乱等情况下便可以使用接口来建立之间的联系。同样,本篇以一个简单的C语言例子来进行接口的实现。

开发环境:

  eclipse集成开发环境、glib库、ubuntu操作系统。

设计流程:

  1、定义一个test接口类,定义4个接口方法

  2、定义一个test类实现这个接口,执行结果就是打印4个方法的命名

  3、主函数调用接口测试

以下是类的设计:

  test接口类:
  testhandler.h

 #ifndef __TEST_HANDLER_H__
#define __TEST_HANDLER_H__ #include <glib-object.h>
#include<glib.h>
G_BEGIN_DECLS #define TYPE_TEST_HANDLER (test_handler_get_type())
#define TEST_HANDLER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), TYPE_TEST_HANDLER, TestHandlerInterface))
#define IS_TEST_HANDLER(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), TYPE_TEST_HANDLER))
#define TEST_HANDLER_INTERFACE(klass) ((TestHandlerInterface*)g_type_interface_peek((klass), TYPE_TEST_HANDLER))
#define GET_TEST_HANDLER_INTERFACE(obj) (G_TYPE_INSTANCE_GET_INTERFACE ((obj), TYPE_TEST_HANDLER, TestHandlerInterface)) typedef struct _TestHandlerInterface TestHandlerInterface; struct _TestHandlerInterface
{
GObjectClass parent_iface; void (*start)(TestHandlerInterface *self);
void (*pause)(TestHandlerInterface *self);
void (*resume)(TestHandlerInterface *self);
void (*stop)(TestHandlerInterface *self);
};
GType test_handler_get_type(void); G_END_DECLS
#endif /* _TEST_HANDLER_H_ */

  testhandler.c

 #include "testhandler.h"

 /************ defines ************/
G_DEFINE_INTERFACE(TestHandler, test_handler, G_TYPE_OBJECT) static void test_handler_default_init(TestHandlerInterface *iface)
{ }

  test类(实现接口的类):

  test.h

 #ifndef __TEST_H__
#define __TEST_H__ #include <glib-object.h> G_BEGIN_DECLS #define TYPE_TEST (test_get_type())
#define TEST(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), TYPE_TEST, Test))
#define TEST_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), TYPE_TEST, TestClass))
#define IS_TEST(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), TYPE_TEST))
#define IS_TEST_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), TYPE_TEST))
#define GET_TEST_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), TYPE_TEST, TestClass)) /************ types ************/
typedef struct _Test Test;
typedef struct _TestClass TestClass;
typedef struct _TestPrivate TestPrivate; struct _Test
{
GObject parent;
};
struct _TestClass
{
GObjectClass parent_class;
}; /************ globals ************/ /************ function declarations ************/
GType test_get_type(void); G_END_DECLS
#endif /* _TEST_H_ */

  test.c 

 #include"test.h"
#include"testhandler.h" /************ defines ************/
static void test_handler_interface_init(TestHandlerInterface *iface);
G_DEFINE_TYPE_WITH_CODE(Test, test, G_TYPE_OBJECT, G_IMPLEMENT_INTERFACE(TYPE_TEST_HANDLER, test_handler_interface_init))
#define GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), TYPE_TEST, TestPrivate)) /************ types ************/
struct _TestPrivate
{ };
/************ function declarations ************/ static void dispose_od(GObject *object);
static void finalize_od(GObject *object);
void start_od(TestHandlerInterface *self);
void pause_od(TestHandlerInterface *self);
void resume_od(TestHandlerInterface *self);
void stop_od(TestHandlerInterface *self);
/************ function implements ************/ static void test_class_init(TestClass *klass)
{
GObjectClass *g_object_class = G_OBJECT_CLASS(klass);
g_type_class_add_private(g_object_class, sizeof(TestPrivate));
g_object_class->dispose = dispose_od;
g_object_class->finalize = finalize_od; } static void test_handler_interface_init(TestHandlerInterface *iface)
{
TestHandlerInterface *testHandlerIface = iface;
testHandlerIface->start=start_od;
testHandlerIface->pause=pause_od;
testHandlerIface->resume=resume_od;
testHandlerIface->stop=stop_od;
} static void test_init(Test *self)
{
TestPrivate *priv = GET_PRIVATE(self);
} static void dispose_od(GObject *object)
{
Test *self = (Test*) object;
TestPrivate *priv = GET_PRIVATE(self);
// 释放创建的对象
G_OBJECT_CLASS(test_parent_class)->dispose(object);
} static void finalize_od(GObject *object)
{
Test *self = (Test*) object;
TestPrivate *priv = GET_PRIVATE(self);
// 释放创建的内存
G_OBJECT_CLASS(test_parent_class)->finalize(object);
} void start_od(TestHandlerInterface *self)
{
TestPrivate *priv = GET_PRIVATE(self);
g_print("start_od!\n");
}
void pause_od(TestHandlerInterface *self)
{
TestPrivate *priv = GET_PRIVATE(self);
g_print("pause_od!\n");
}
void resume_od(TestHandlerInterface *self)
{
TestPrivate *priv = GET_PRIVATE(self);
g_print("resume_od!\n");
}
void stop_od(TestHandlerInterface *self)
{
TestPrivate *priv = GET_PRIVATE(self);
g_print("stop_od!\n");
}

  主函数:

 #include<glib.h>
#include<stdio.h>
#include<stdlib.h>
#include"test.h"
#include"testhandler.h"
#include<string.h>
int main(void)
{
Test *test = g_object_new(TYPE_TEST,NULL);
if (test != NULL)
{
GET_TEST_HANDLER_INTERFACE(test)->start(TEST_HANDLER(test));
GET_TEST_HANDLER_INTERFACE(test)->pause(TEST_HANDLER(test));
GET_TEST_HANDLER_INTERFACE(test)->resume(TEST_HANDLER(test));
GET_TEST_HANDLER_INTERFACE(test)->stop(TEST_HANDLER(test));
}
return EXIT_SUCCESS;
}

总结:

  从主函数中的测试代码中我们可以看出,调用接口的一方或类还是需要联系接口方法的实现类,耦合度还是较高,而在JAVA中接口则能够很好的分离两方。所以在C语言中接口主要是用于上层结构设计,同时由于gobject并未

能很好的实现接口,所以在项目中为了是两者很好的分离,其中一个办法就是通过指针调用来尽量做到低耦合,例如使用重载等方法。

glib实践篇:接口定义与实现的更多相关文章

  1. Java 8新特性-2 接口定义增强

    为了解决当原有的接口中方法不足时,向原有的接口中添加新的方法,该接口下的N多实现类也需要重写该方法的问题!Java8引入了接口定义增强概念! Java8 打破了原有的接口的方法定义: 公共的.抽象的  ...

  2. java数据结构_附11_图的接口定义

    图的接口定义 Graph public class UnsupportedOperation extends RuntimeException {public UnsupportedOperation ...

  3. [Asp.net 5] Configuration-新一代的配置文件(接口定义与基础实现)

    关于配置文件的目录:[Asp.net 5] Configuration-新一代的配置文件 本系列文章讲的是asp.net 5(Asp.net VNext)中的配置文件部分,工程下载地址为:https: ...

  4. IOleItemContainer的接口定义

      IOleItemContainer的接口定义

  5. IBindCtx接口定义

    IBindCtx接口定义

  6. USB 3.0连接器引脚、接口定义及封装尺寸

    上篇整理了USB 2.0A型.B型和Mini USB接口定义及封装,本文补充USB 3.0接口定义,USB 3.0采用的双总线结构,在速率上已经达到4.8Gbps,所以称为Super speed,在U ...

  7. USB 2.0 A型、B型、Mini和Micro接口定义及封装

    USB全称Universal Serial Bus(通用串行总线),目前USB 2.0接口分为四种类型A型.B型.Mini型还有后来补充的Micro型接口,每种接口都分插头和插座两个部分,Micro还 ...

  8. 数据结构 链式哈希表(Hash Table)的接口定义与实现分析(完整代码)

    链式哈希表的接口定义 关于哈希表与链式哈希表的描述可以参阅:http://www.cnblogs.com/idreamo/p/7990860.html 链式哈希表的操作与属性有:初始化.销毁.插入元素 ...

  9. 开地址哈希表(Hash Table)的接口定义与实现分析

    开地址哈希函数的接口定义 基本的操作包括:初始化开地址哈希表.销毁开地址哈希表.插入元素.删除元素.查找元素.获取元素个数. 各种操作的定义如下: ohtbl_init int ohtbl_init ...

  10. CDN页面刷新接口定义[高升]

    一 . 任务 分发 工作流程步骤 1. 合作方按照高升定义的 json 数据格式向高升分发接口 post 任务,高升分发接口会根据接收情况即时反馈接收成功还是失败的结果.二 . 高升 分发 接口 定义 ...

随机推荐

  1. 缓存,spring

    applicationcontext.xml xmlns:cache="http://www.springframework.org/schema/cache" xsi:schem ...

  2. MVC 5.1的遭遇:“已添加了具有相同键的项”

    ASP.NET MVC 3升级至MVC 5.1的遭遇:“已添加了具有相同键的项”   最近将一个项目从ASP.NET MVC 3升级至刚刚发布的ASP.NET MVC 5.1,升级后发现一个ajax请 ...

  3. node-webkit入门

    node-webkit入门   一.简介 node-webkit 是一个基于chromium与node.js的应用程序运行器,它允许开发者使用web技术编写桌面程序.通过Node.js和WebKit技 ...

  4. 揭开redis神秘面纱

    一直听别人说NoSQL,以前一直不明白,这到底是什么东西,今天听过我们涛哥的讲解,略有小感,特此小记. NoSQL(NoSQL = Not Only SQL),意为反SQL运动,是一项全新的数据库革命 ...

  5. MongoDB学习(翻译5)

    C#驱动序列化文档对象 介绍 本文档基于C#官方驱动1.8版本. 本节C#驱动教程谈论C#类到BSON对象的序列化和反序列化.序列化是映射一个对象到可保存到MongoDB库中BSON对象的过程,反序列 ...

  6. struts2 action 接受数组参数为Null的问题

    public List<FormulaDetail> formulaDetails; public List<FormulaDetail> getFormulaDetails( ...

  7. 使用 App Studio 快速定制一个你自己的专属应用

    使用 App Studio 快速定制一个你自己的专属应用 如果已有做一个手机应用的想法,只需要一些简单的图片,视频,或者RSS源,就可以通过App Studio制作出你心仪的应用! App Studi ...

  8. Jquery 图片轮播实现原理总结

    Jquery 图片轮播实现原理总结 以前要做图片轮播效果的时候,总是在网上找一段jquery的复制粘贴进去,只索取不奉献,今个就把我对这个的实现原理讲解一下. 首先说下,我在网上找的例子全是用的UL ...

  9. 适配器模式及C++实现

    适配器模式及C++实现 适配器模式 适配器模式是很好理解的模式了,生活中也非常常见,什么插头2口转3口,什么USB转PS2,这都算是适配器模式.说白了,就是如果有一些东西提供的接口你很像用,但是你手头 ...

  10. Cygwin 各种情况下中文乱码--终极解决方案

    0.引言 本人从进公司以来一直负责公司Android平台下产品的NDK开发,用的工具: 01. Google的adt-bundle(集成了eclipse和sdk) 02. NDK 03. Cygwin ...