c
Chapter 1

C language

Subsections of C language

Using gniplot on C

操作方法

gnuplotをC言語のプログラムから制御するには,パイプを使うのが最も簡単である.ここでは,C言語のプログラムによりパイプの生成しgnuplotを起動を行い,パイプを通してコマンドを送る.C言語のプログラム内にコマンドを記述することにより,プログラマーの意図したとおりにgnuplotを操作することができる.

  1. パイプを開く

    1. パイプを開くためには,ファイルポインターをつかう.そのためファイルポインターを格 納する変数を用意しなくてはならない.パイプの先もファイルとして扱われるのである.
      FILE *hoge;
      
    2. 次にgnuplotを立ち上げて,そこにパイプを接続する必要がある.次のようにする.
      hoge = popen("gnuplot -persist","w");
      
    3. popen()関数がパイプを開く命令である.これで,gnuplot が立ち上がり,パイプを 通して,コマンドを送ることができる.オプションのpersistで,gnuplotが終了し てもグラフが残るようにしている.そうしないと,コンピューターの動作は高速なので, gnuplotは一瞬にして終了し,グラフが消えてしまい,ほとんど動作内容が分からなく なる.popen()関数の戻り値はパイプの情報を示すファイルポインターである.この ファイルポインターを指定して,コマンドを送ることになる.
  2. パイプを通してコマンドを送る パイプを通して,gnuplotにコマンドを送るのはfprintf()関数を使う. c fprintf(hoge, "plot sin(x)\n"); このfprintfを使って,gnuplotにいくらでもコマンドを送ることができる.あたかも,C言語の向こう側でgnuplotが立ち上がって,それから命令を送っているかのように動作する.このようなことができるのが,コマンドを打ち込むCharacter-based User Interface(CUI)の良いところである.

  3. パイプを閉じる すべての動作が終了したならば,パイプを閉じなくてはならない.これも,ファイルの操作と全く同じである. c pclose(hoge);

(例)三角関数のグラフ作成プログラム

1 #include <stdio.h>
2 
3 int main(void){
4   FILE *gp;
5 
6   gp = popen("gnuplot -persist","w");
7   fprintf(gp, "plot sin(x)\n");
8 
9   pclose(gp);
10 
11   return 0;
12 }

参考文献

Method of file division

ファイル分割

c言語のファイル分割では関数等を書き込むファイル.c``.hファイルとmain関数を書き込むファイルの3つのファイルを用意する

  1. 関数を書き込むcalc.cファイル

    #ifndef _CALC_H_
    #define _CALC_H_
    
    //  関数avgのプロトタイプ宣言
    double avg(double,double);
    
    #endif // _CALC_H_
    
  2. calc.hファイル

    #include "calc.h"
    
    //  平均値を求める関数
    double avg(double l,double m){
        //  引数l,mの平均値を求め、rに代入する。
        double r = (l + m) / 2.0;
        return r;
    }
    

    このファイルでは次のようにファイルに書き込み、プロトタイプ宣言を行う

    #ifnfdef _(大文字で記述したファイル名)_H_
    #define _(大文字で記述したファイル名)_H_
    
    プロトタイプ宣言;
    プロトタイプ宣言;
    
    
    
    #endif // _(大文字で記述したファイル名)_H_
    

    ここで登場した#ifndef``#define``#endifはマクロといい、二重インクルードを防いでいる

  3. main関数を書き込むmain.cファイル

    #include <stdio.h>
    #include "calc.h"
    
    void main(){
    double d1,d2,d3;
    double a = 1.2,b = 3.4,c = 2.7;
    //   同じ計算が3回(関数を呼び出して計算)
    d1 = avg(a,b);
    d2 = avg(4.1,5.7);
    d3 = avg(c,2.8);
    printf("d1 = %f,d2 = %f,d3 = %f¥n",d1,d2,d3);
    }
    

コンパイルの仕方

gcc はコマンドラインで与えられたソースファイルしか読み込まないため、すべての.cソースファイルをまとめ上げて実行する必要がある

下記2パターンの方法で実行が可能

  1. (即席回答)1コマンドで

    $ gcc main.c calc.c
    

    ※-o オプションで実行ファイル名を指定することも可能

    この方法ではオブジェクトファイル*.oは最後に掃除・削除されるため残らない

  2. 3コマンドで

    $ gcc -c main.c
    $ gcc -c calc.c
    $ gcc main.o calc.o
    

    -c オプションではオブジェクトファイル*.oを作るところまでしてくれる

    この方法では途中までの.oファイルも残るため、途中でコンパイルエラーが起きてもそれまでのオブジェクトファイルは残るという利点がある。したがってたくさんの*.cファイルで構成される実務プログラムではこの方法で1本ずつコンパイルシていくのが一般的担っている。

c言語コンパイルのちょこっと解説

gcc は、3つの下請けを順次起動する、親玉に過ぎません。

  1. プリプロセッサ - #include や #define を処理、本来(?)のC言語ソースにする
  2. コンパイラ - *.c をコンパイルし、オブジェクトファイル *.o を作る
  3. リンカ - 1個以上の *.o をまとめあげ、1個の実行形式ファイル(Windowsなら *.exe)を作る

gcc の -c オプションは、「上記2.まででいいよ」指示です。

即席回答 1. のやりかたは、これを全部まとめて1回にしてるだけ。

*.o は、実は途中でできてますが、こういう要求のしかたをされたgcc は、最後にキレイに掃除・削除してしまいます。

参考