Visual Stdio 环境下使用 GSL (GNU Scientific Library)

经測试。这里的方法不适用于VS2015。

* 这篇文章有点过时了。建议从以下网址下载能够在 vs 环境下编译的 GSL:*

https://github.com/BrianGladman/gsl

GNU Scientific Library (GSL)是一个开源的科学计算的函数库,功能非常强大。

网上介绍它的文章非常多,并且 GSL 的文档也写的非常的好,属于那种特别easy上手的函数库。

这里就不多对 GSL 进行介绍了。

今天要讲的是怎样在 Visual stdio 环境下使用这个库。事实上这方面的内容网上也有一些。只是採用的方法大多不太好。

有的是直接下载 GSL for Widows 来使用,可是这个 GSL for Widows 是 2006 年的GSL 1.8 ,古董级的版本号了,这个版本号缺少的功能太多。

还有一种方法是改造 MinGW 编译的生成的 dll。

事实上不同的 C 语言编译器编译生成的 dll 仅仅要遵守同样的 C calling Conven,原则上是能够通用的。可是不同的编译器自带的库函数是有区别的。

比方说 GSL 库中代码常常会用到 hypot 函数,这个函数在 MinGW 工具链中属于标准数学库中的函数。能够直接使用。可是 Visual stdio 的数学库中却没有这个函数。因此,直接拿来用 MinGW 的 gsl 是不行的,会在 link 阶段遇到缺少各种函数的定义的问题。

因此,假设想要在 Visual Stdio 环境下使用 GSL 最好的办法是又一次编译 GSL 代码。简单说这又分成了两个不同的道路。

  • 使用 Visual Stdio 中的 C 编译器编译 GSL
  • 使用 MinGW 中的 C 编译器编译 GSL

当中第一种方法相对来说麻烦些。须要建立个 Visual Stdio project。将相关的代码加入到project中,还须要改动个别几处 gsl 的代码(主要是由于 Visual Stdio 的 C 编译器不支持 C99 标准中的 inline 特性,GSL 代码中有几处不够严谨没有考虑这个问题)。

另外就是 Visual Stdio 的编译器生成 DLL 须要通过 def 文件来指定导出函数,这个 def 文件须要我们自己来生成。gsl 的源码中没有给出。由于这样的方法比較繁琐,对新手来说失败的可能性非常大,因此我今天主要介绍还有一种方法。

使用 MinGW 中的 C 编译器编译 GSL

熟悉 Linux 下软件编译的同学肯定都知道这样的源码编译安装都是标准的三个步骤:

  • ./configure
  • make
  • make install

我们编译 GSL 自然也摆脱不了这个工序。

当然在这之前我们须要有 MinGW 工具链和 MSYS 环境。

在这里我建议大家使用 MSYS2,关于 MSYS2 的安装。能够參考我写的一篇短文:

http://blog.csdn.net/liyuanbhu/article/details/39397931

在工具链准备齐全之后。将 gsl-1.16.tar.gz 解压缩到 MSYS2 的home 文件夹中。之后就是 ./configure 。

这个过程会比較长。可能要用 3、5分钟。

之后在 gsl-1.16 的根文件夹下就会有 config.h 文件了。

对这个文件我们还须要改造一番。之所以要改造是由于这个文件是为 MinGW gcc 工具链准备的,对 Visual Stdio 开发工具来说不是那么适合。

以下就具体的说说这个 config.h 文件的内容。

config.h 的开头 25 行是这样的。

/* config.h.  Generated from config.h.in by configure.  */
/* config.h.in. Generated from configure.ac by autoheader. */ /* Disable deprecated functions and enums while building */
#define GSL_DISABLE_DEPRECATED 1 /* Define if you have inline with C99 behavior */
#define HAVE_C99_INLINE 1 /* Define to 1 if you have the declaration of `acosh', and to 0 if you don't.
*/
#define HAVE_DECL_ACOSH 1 /* Define to 1 if you have the declaration of `asinh', and to 0 if you don't.
*/
#define HAVE_DECL_ASINH 1 /* Define to 1 if you have the declaration of `atanh', and to 0 if you don't.
*/
#define HAVE_DECL_ATANH 1 /* Define to 1 if you have the declaration of `expm1', and to 0 if you don't.
*/
#define HAVE_DECL_EXPM1 1

#define HAVE_C99_INLINE 1 表明编译器支持 C99。尽管 VS 编译器不支持 C99 ,可是这句我们仍然能够保留。 由于 GSL 实际上仅仅是使用到了 C99 的 inline ,其它的特性都没用到。 而 VS 编译器实际上也是支持 inline 的。关于这个 inline 的支持,我们后面还会具体的说。

acosh、asinh、atanh、expm1 这四个函数 VS 的标准库中都是不支持的。

所以要将这四个 1 都改动成 0。

喜欢刨根问底的同学可能会问。VS 中缺少这些函数。会不会影响到 gsl 的功能呢。答案当然是否定的。这些不属于 C 语言标准的函数 GSL 都自己实现了一遍。有些放到了 sys 子文件夹中,有些放到了 utils 文件夹中,还有些分散到其它文件夹。

可是 GSL 实现都在函数名前加了 gsl 前缀。比方 expm1 函数,在 gsl 中实现为:

double gsl_expm1 (const double x)

假设 config.h 中配置为:

#define HAVE_DECL_EXPM1 0

则在 gsl 中全部用的 expm1 函数的地方都会调用 gsl_expm1 函数。

其它须要更改的地方还包含:

#define HAVE_DECL_FINITE 0
#define HAVE_DECL_FREXP 0
#define HAVE_DECL_HYPOT 0
#define HAVE_DECL_ISFINITE 0
#define HAVE_DECL_ISINF 0
#define HAVE_DECL_ISNAN 0
#define HAVE_DECL_LDEXP 0
#define HAVE_DECL_LOG1P 0
#define HAVE_IEEEFP_H 0
#define HAVE_IEEE_DENORMALS 0
#define HAVE_STRDUP 0
#define HAVE_STRINGS_H 0
#define HAVE_UNISTD_H 0

当中 hypot 函数实际上是有的。可是依照 微软的说法:

This POSIX function is deprecated beginning in Visual C++ 2005.

所以我们还是应该不用它。

有了 config.h 文件后我们就能够进行下一步了。

  • make

之后是漫长的等待。编译完毕之后我们须要的文件就都有了。

gsl-1.16\cblas.libs 文件夹中能够找到例如以下文件:

  • libgslcblas.a
  • libgslcblas.dll.a
  • libgslcblas-0.dll

gsl-1.16.libs 文件夹中能够找到例如以下文件:

  • libgsl.a
  • libgsl.dll.a
  • libgsl-0.dll

将这些文件都拷贝出来。 .a 文件改名为 .lib。

头文件在 gsl-1.16\gsl 文件夹中,能够将这个文件夹完整拷贝出来。

我们能够建立一个文件夹,名为 gsl-1.16-vs。

然后建立三个子文件夹,各自是 :

  • include
  • lib
  • bin

将头文件所在的 gsl 文件夹拷贝的 include 文件夹中, .lib 文件复制到 lib 文件夹中,.dll 文件复制到 bin 文件夹中。

至此,我们的工作就完毕了大半了。

大家能够试试我们生成的 lib 文件和 dll 文件。具体怎样在 VS 中使用第三方的库。网上介绍文章有非常多,我就不多说了。

gsl 帮助文件里的第一个样例:

#include <stdio.h>
#include <gsl/gsl_sf_bessel.h>
int main(int argc, char *argv[])
{
double x = 5.0;
double y = gsl_sf_bessel_J0 (x);
printf ("J0(%g) = %.18e\n", x, y);
return 0;
}

这个样例如今能够编译通过并顺利的运行了,得到的结果也是正确的。

可是这时我们还不能高兴太早。 Visual Stdio 还给我们预备了一个大坑等着我们往里跳呢。这个大坑就是 VS 编译器不支持 C99。当然也包含不支持 C99 的 inline。

所以在编译以下的代码时就会报很多错误。

#define HAVE_INLINE 1
#include "stdafx.h"
#include <stdio.h>
#include <gsl/gsl_vector.h> int _tmain(int argc, _TCHAR* argv[])
{
int i;
gsl_vector * v = gsl_vector_alloc (10);
for (i = 0; i < 10; i++)
{
gsl_vector_set (v, i, 1.23 + i);
}
for (i = 0; i < 10; i++)
{
printf ("v_%d = %g\n", i, gsl_vector_get (v, i));
}
gsl_vector_free (v);
getchar();
return 0;
}

报的错误主要是:

error C2054: 在“inline”之后应输入“(”

解决问题就要改动 gsl_inline.h 这个文件。这个文件有例如以下几行。

#ifdef HAVE_INLINE
# if defined(__GNUC_STDC_INLINE__) || defined(GSL_C99_INLINE) || defined(HAVE_C99_INLINE)
# define INLINE_DECL inline /* use C99 inline */
# define INLINE_FUN inline
# else
# define INLINE_DECL /* use GNU extern inline */
# define INLINE_FUN extern inline
# endif
#else
# define INLINE_DECL /* */
#endif

将其改动为 :

#ifdef HAVE_INLINE
# if defined(__GNUC_STDC_INLINE__) || defined(GSL_C99_INLINE) || defined(HAVE_C99_INLINE)
# define INLINE_DECL inline /* use C99 inline */
# define INLINE_FUN inline
# else
# define INLINE_DECL /* use GNU extern inline */
# define INLINE_FUN __inline
# endif
#else
# define INLINE_DECL /* */
#endif

这样再编译就没有错误了。

我将编译好gsl放到了以下的链接里,有须要能够直接下载。

http://download.csdn.net/detail/liyuanbhu/9009755

Visual Stdio 环境下使用 GSL (GNU Scientific Library)的更多相关文章

  1. 【C++】GSL(GNU Scientific Library) 的安装及在 Visual Studio 2017 中的使用

    GSL 是 GNU 开发并维护的科学计算的库,其中包括: 复数 多项式的根 特殊函数 向量和矩阵 排列 排序 BLAS支持 线性代数 Eigensystems 快速傅立叶变换 正交 随机数 准随机序列 ...

  2. (转载)Ubuntu 安装GNU Scientific library(GSL)

    背景: Blei的hlda的C语言实现需要使用C语言的科学计算包GSL,因此决定安装.由于在windows下安装极其繁琐,先在Linux上安装之. 系统环境: Linux version 2.6.35 ...

  3. Ubuntu 安装GNU Scientific library(GSL)

    注: 此系列为自己之前所搭建网站内容. 由于论文数据处理的需要,需要使用libeemd这个包,需要安装gsl科学库,windows下没有办法,只能转战ubuntu进行科学计算. GSL(GNU Sci ...

  4. GNU scientific library

    GNU scientific library 是一个强大的C,C++数学库.它涉及的面很广,并且代码效率高,接口丰富.正好最近做的一个项目中用到多元高斯分布,就找到了这个库. GNU scientif ...

  5. Visual Studio2008环境下查找C#中方法的“查看所有引用”

    在Visual Studio开发环境下,想必F12我们都很熟悉了,有没有用过“查看所有引用”呢? 尤其是在一个解决方案中,包含了很多项目,彼此相互的调用是很常见的,例如三层架构, BLL调用DAL,D ...

  6. ubuntu14.04 下安装 gsl 科学计算库

    GSL(GNU Scientific Library)作为三大科学计算库之一,除了涵盖基本的线性代数,微分方程,积分,随机数,组合数,方程求根,多项式求根,排序等,还有模拟退火,快速傅里叶变换,小波, ...

  7. 如何使用SOIL在VS2012的 C++环境下显示图片

    先看下效果. 这是一个很无聊的功能....首先说下,我做这个功能的初衷并不是为了实现在控制台中显示图片...(这貌似很无聊) 而是因为自己想做用C做一个游戏:http://q.cnblogs.com/ ...

  8. GSL--GNU Scientific Library 小记

    摘自http://qianjigui.iteye.com/blog/847612 GSL(GNU Scientific Library)是一个 C 写成的用于科学计算的库,下面是一些相关的包 Desi ...

  9. WIN7环境下CUDA7.5的安装、配置和测试(Visual Studio 2010)

    以下基于"WIN7(64位)+Visual Studio 2010+CUDA7.5". 系统:WIN7,64位 开发平台:Visual Studio 2010 显卡:NVIDIA ...

随机推荐

  1. theme- 工作原理

    首先看一下theme中的设置,代码如下 <?xml version="1.0" encoding="utf-8"?> <resources&g ...

  2. SuSe Linux 10 企业服务器搭建双机集群配置实例

      650) this.width=650;" onclick="window.open("http://blog.51cto.com/viewpic.php?refim ...

  3. BZOJ3514: Codechef MARCH14 GERALD07加强版(LCT,主席树)

    Description N个点M条边的无向图,询问保留图中编号在[l,r]的边的时候图中的联通块个数. Input 第一行四个整数N.M.K.type,代表点数.边数.询问数以及询问是否加密.接下来M ...

  4. CISP/CISA 每日一题

    CISA 业务流程控制鉴证中要考虑的特定因素: 1.流程图 2.流程控制 3.在流程中评估业务风险 4.对最佳实践进行标杆管理 5.角色与责任 6.活动与任务 7.数据限制   信息系统审计师的任务是 ...

  5. 【2017 Multi-University Training Contest - Team 7】Hard challenge

    [Link]:http://acm.hdu.edu.cn/showproblem.php?pid=6127 [Description] 平面上有n个点,每个点有一个价值,每两个点之间都有一条线段,定义 ...

  6. 决策树2 -- CART算法

    声明: 1,本篇为个人对<2012.李航.统计学习方法.pdf>的学习总结.不得用作商用,欢迎转载,但请注明出处(即:本帖地址). 2,因为本人在学习初始时有非常多数学知识都已忘记.所以为 ...

  7. Android 小米盒子游戏手柄按键捕获 - 能获取到的 home 键依旧是个痛

    Android 小米盒子游戏手柄按键捕获 太阳火神的漂亮人生 (http://blog.csdn.net/opengl_es) 本文遵循"署名-非商业用途-保持一致"创作公用协议 ...

  8. C#程序集引入无效的解决方法

    在项目类库中已经引用了相关了类库,生成解决方案也没问题,但是到了后置代码,通过using引用其他类库的时候,再生成解决方案或者生成单个类库,就会报“未能找到类型或命名空间“xxx"(是否缺少 ...

  9. JAVA 水题

    纯粹是让我来掌握熟练度的. 1.金蝉素数 某古寺的一块石碑上依稀刻有一些神秘的自然数. 专家研究发现:这些数是由1,3,5,7,9 这5 个奇数字排列组成的5 位素数,且同时去掉它的最高位与最低位数字 ...

  10. js进阶 13 jquery动画函数有哪些

    js进阶 13 jquery动画函数有哪些 一.总结 一句话总结: 二.jquery动画函数有哪些 原生JavaScript编写动画效果代码比较复杂,而且还需要考虑兼容性.通过jQuery,我们使用简 ...