Download : sample-001.c ( utf8 版 )
/*
* 2016/11/11 sample-001.c
*/
/*
* sizeof 演算子
* 型名を指定する事により、そのサイズ(byte 単位)を得る事ができる
*
* 利用方法
* コンパイル
* cc -I../include -o sample-001.exe sample-001.c
* 実行
* ./sample-001.exe
*/
#include <stdio.h>
/*
* main 関数
*/
int main ( int argc, char *argv[] ) {
printf ( "sizeof ( char ) = %d\n", sizeof ( char ) );
printf ( "sizeof ( int ) = %d\n", sizeof ( int ) );
printf ( "sizeof ( double ) = %d\n", sizeof ( double ) );
return 0;
}
$ ./sample-001.exe sizeof ( char ) = 1 sizeof ( int ) = 4 sizeof ( double ) = 8 $
Download : sample-002.c ( utf8 版 )
/*
* 2016/11/11 sample-002.c
*/
/*
* sizeof 演算子
* 変数名を指定する事により、そのサイズ(byte 単位)を得る事ができる
*
* 利用方法
* コンパイル
* cc -I../include -o sample-002.exe sample-002.c
* 実行
* ./sample-002.exe
*/
#include <stdio.h>
/*
* main 関数
*/
int main ( int argc, char *argv[] ) {
char cvar;
int ivar;
double dvar;
printf ( "sizeof ( cvar ) = %d\n", sizeof ( cvar ) );
printf ( "sizeof ( ivar ) = %d\n", sizeof ( ivar ) );
printf ( "sizeof ( dvar ) = %d\n", sizeof ( dvar ) );
return 0;
}
$ ./sample-002.exe sizeof ( cvar ) = 1 sizeof ( ivar ) = 4 sizeof ( dvar ) = 8 $
Download : sample-003.c ( utf8 版 )
/*
* 2016/11/11 sample-003.c
*/
/*
* sizeof 演算子
* 配列名を指定する事により、そのサイズ(byte 単位)を得る事ができる
* type array[SIZE] の時 sizeof( array ) = sizeof(type) * SIZE
*
* 利用方法
* コンパイル
* cc -I../include -o sample-003.exe sample-003.c
* 実行
* ./sample-003.exe
*/
#include <stdio.h>
/*
* main 関数
*/
int main ( int argc, char *argv[] ) {
char cary[100];
int iary[100];
double dary[100];
printf ( "sizeof ( cary ) = %d\n", sizeof ( cary ) );
printf ( "sizeof ( iary ) = %d\n", sizeof ( iary ) );
printf ( "sizeof ( dary ) = %d\n", sizeof ( dary ) );
return 0;
}
$ ./sample-003.exe sizeof ( cary ) = 100 sizeof ( iary ) = 400 sizeof ( dary ) = 800 $
Download : sample-004.c ( utf8 版 )
/*
* 2016/11/11 sample-004.c
*/
/*
* sizeof 演算子
* 値を指定する事もできる
*
* 利用方法
* コンパイル
* cc -I../include -o sample-004.exe sample-004.c
* 実行
* ./sample-004.exe
*/
#include <stdio.h>
/*
* main 関数
*/
int main ( int argc, char *argv[] ) {
printf ( "sizeof ( 'a' ) = %d\n", sizeof ( 'a' ) );
/* sizeof ( int ) [整数] になっている */
printf ( "sizeof ( 123 ) = %d\n", sizeof ( 123 ) );
printf ( "sizeof ( 12.3 ) = %d\n", sizeof ( 12.3 ) );
return 0;
}
$ ./sample-004.exe sizeof ( 'a' ) = 4 sizeof ( 123 ) = 4 sizeof ( 12.3 ) = 8 $
Download : sample-005.c ( utf8 版 )
/*
* 2016/11/11 sample-005.c
*/
/*
* sizeof 演算子
* 式のサイズも得られる
* char 型のデータは、計算の時に、int 型に昇格する
*
* 利用方法
* コンパイル
* cc -I../include -o sample-005.exe sample-005.c
* 実行
* ./sample-005.exe
*/
#include <stdio.h>
/*
* main 関数
*/
int main ( int argc, char *argv[] ) {
char ch;
char dh;
printf ( "sizeof ( ch ) = %d\n", sizeof ( ch ) );
/* sizeof ( char ) [文字] になっている */
printf ( "sizeof ( ch + dh ) = %d\n", sizeof ( ch + dh ) );
/* sizeof ( int ) [整数] になっている */
/* 無条件の型の昇格がおきている */
return 0;
}
$ ./sample-005.exe sizeof ( ch ) = 1 sizeof ( ch + dh ) = 4 $
Download : sample-006.c ( utf8 版 )
/*
* 2016/11/11 sample-006.c
*/
/*
* 型の昇格
* int 型から double 型への変換
*
* 利用方法
* コンパイル
* cc -I../include -o sample-006.exe sample-006.c
* 実行
* ./sample-006.exe
*/
#include <stdio.h>
/*
* main 関数
*/
int main ( int argc, char *argv[] ) {
int num;
int mum;
printf ( "sizeof ( num ) = %d\n", sizeof ( num ) );
printf ( "sizeof ( num + 'A' ) = %d\n", sizeof ( num + 'A' ) );
printf ( "sizeof ( num + mum ) = %d\n", sizeof ( num + mum ) );
printf ( "sizeof ( num + 1.0 ) = %d\n", sizeof ( num + 1.0 ) );
return 0;
}
$ ./sample-006.exe sizeof ( num ) = 4 sizeof ( num + 'A' ) = 4 sizeof ( num + mum ) = 4 sizeof ( num + 1.0 ) = 8 $
Download : sample-007.c ( utf8 版 )
/*
* 2016/11/11 sample-007.c
*/
/*
* 型の変換
* 代入では、必要に応じて型変換が行わる
*
* 利用方法
* コンパイル
* cc -I../include -o sample-007.exe sample-007.c
* 実行
* ./sample-007.exe
*/
#include <stdio.h>
/*
* main 関数
*/
int main ( int argc, char *argv[] ) {
char ch = 'A'; /* そもそも 'A' は int 型 */
int num = 'A';
double fp = 'A'; /* int 型から double 型へ */
ch = ch - 'A' + 'a'; /* int 型から char 型へ */
ch = num; /* int 型から char 型へ */
num = fp; /* double 型から int 型へ */
printf ( "ch = %c\n", ch );
printf ( "num = %d\n", num );
printf ( "fp = %f\n", fp );
return 0;
}
$ ./sample-007.exe ch = A num = 65 fp = 65.000000 $
Download : sample-008.c ( utf8 版 )
/*
* 2016/11/11 sample-008.c
*/
/*
* 型の変換
* サイズの大きい方から、小さい方への変換は危険
*
* 利用方法
* コンパイル
* cc -I../include -o sample-008.exe sample-008.c
* 実行
* ./sample-008.exe
*/
#include <stdio.h>
/*
* main 関数
*/
int main ( int argc, char *argv[] ) {
char ch = 'A';
int num = 'A';
double fp = 'A';
/* 個々に適切な値をいれれば問題はない */
printf ( "[適切な値]\n" );
printf ( "\tch = '%c' [%d]\n", ch, ch );
printf ( "\tnum = %d\n", num );
printf ( "\tfp = %f\n", fp );
/* char 型にはいらないサイズの値をいれると ?? */
num = 1000; /* 1000 => 256 なので、1000 は char 型に入らない */
ch = num; /* 代入を行うとどうなるか */
printf ( "[char に大きな値]\n" );
printf ( "\tch = '%c' [%d]\n", ch, ch );
printf ( "\tnum = %d\n", num );
/* int 型にはいらないサイズの値をいれると ?? */
fp = 1000000000000;
num = fp;
ch = fp;
printf ( "[int に大きな値]\n" );
printf ( "\tch = '%c' [%d]\n", ch, ch );
printf ( "\tnum = %d\n", num );
printf ( "\tfp = %f\n", fp );
return 0;
}
$ ./sample-008.exe [適切な値] ch = 'A' [65] num = 65 fp = 65.000000 [char に大きな値] ch = '?' [-24] num = 1000 [int に大きな値] ch = ' ' [0] num = -2147483648 fp = 1000000000000.000000 $
/*
* 課題 20161028-01
*
* 2016/10/28 20161028-01-QQQQ.c
*
* 浮動小数点数の配列の要素内の数値の総和を求める。
*/
#include <stdio.h>
/*
* 浮動小数点数の配列の要素内の数値の総和を求める。
*
* 利用方法
* コンパイル
* cc -o BASENAME.exe 20161028-01-QQQQ.c
* 実行
* ./BASENAME.exe
*/
#include <stdio.h>
/*
* double dsum ( double ary[], int size )
* 浮動小数点数の配列の要素内の数値の総和を求める関数
* double ary[]; 総和を求める要素を含む配列
* int size; 配列のサイズ
*/
double dsum ( double ary[], int size ) {
/* ary[] の中がかかれていない */
/* サイズは、別に渡す必要があり、その情報は、
第二引数の size で渡している */
/* ary には、先頭の場所に関する情報(ポインター値)だけしかわたらない */
double sum = 0.0; /* 総和は最初は 0 */
int i; /* 配列の要素を参照する添字変数 */
/*
目的:
ary[0] + ary[1] + ... + ary[size-1]
-> sum に記録したい
もし、size が 3 であれば、
sum = ary[0] + ary[1] + ary[2]
とすればよい。
一般的には
sum = ary[0] + ary[1] + ... + ary[size-1]
size は、その時によって異なる
後から指定する
しなきゃいけないので、面倒だし、複雑になる
その時にすればよいので、汎用性が高い
[Step 0]
sum = ary[0] + ary[1] + ... + ary[size-1]
[Step 1] 命令の長さが可変なものは、プログラムでかけない
同じ長さの命令の繰り返しであらわす
(そのかわりに、繰り返し回数を可変にする)
sum = ary[0]
sum = sum + ary[1]
sum = sum + ary[2]
...
sum = sum + ary[size-1]
[Step 2] 繰り返しで、問題を解く場合は、例外を減らす
sum = 0.0
sum = sum + ary[0]
sum = sum + ary[1]
sum = sum + ary[2]
...
sum = sum + ary[size-1]
[Step 3] 命令の中の変化する部分は、変数にしてしまう
sum = 0.0
i = 0
sum = sum + ary[i]
i = 1
sum = sum + ary[i]
i = 2
sum = sum + ary[i]
...
i = size-1
sum = sum + ary[i]
[Step 4] 変数の変化を規則的な命令で実現する
sum = 0.0
i = 0
sum = sum + ary[i]
i = i + 1
sum = sum + ary[i]
i = i + 1
sum = sum + ary[i]
...
i = i + 1
sum = sum + ary[i]
i = i + 1
[Step 5] while にしてしまう
sum = 0.0
i = 0
while ( i < size ) {
sum = sum + ary[i]
i = i + 1
}
[Step 6] for にしてしまう
sum = 0.0
for ( i = 0: i < size; i = i + 1 ) {
sum = sum + ary[i]
}
*/
for ( i = 0; i < size; i++ ) { /* i = 0 〜 sum - 1 の間.. */
/*
** この部分を完成させなさい
*/
/* 「sum += ary[i]」とも書ける */
}
return sum; /* 結果を返す */
}
/*
* main
*/
#define ARY_SIZE 5
int main( int argc, char *argv[] )
{
double data[ARY_SIZE]; /* 大きさ ARY_SIZE の配列の宣言 */
int i; /* 配列の要素を参照する添字変数 */
double sum; /* 総和の計算結果を保持する */
printf ( "%d 個のデータを入力します。\n", ARY_SIZE );
for ( i = 0; i < ARY_SIZE; i++ ) {
printf ( "%d 番目の数値を入力してください : ", i + 1 );
/*
** この部分を完成させなさい
*/
scanf ( "%lf", &data[i] );
}
sum = dsum ( data, ARY_SIZE );
/* 引数は、配列名(ポインター値) と、そのサイズの両方を指定する */
printf ( "入力されたデータの総和は %f です。\n", sum );
return 0;
}
/*
2, 4, 6, 8, ...
2 2 2
a_0 = 2
a_{n+1} = a_{n} + 2
a_{n} = 2n
/*
* 課題 20161028-02
*
* 20161028 20161028-02-QQQQ.c
*
* 文字列の途中に文字を挿入する
*
* 利用方法
* コンパイル
* cc -o BASENAME.exe 20161028-02-QQQQ.c
* 実行
* ./BASENAME.exe
*/
#include <stdio.h>
/*
*
*/
/*
* main
*
*/
#define CSIZE 10
#define EOS '\0'
/*
課題
"abcd" -> "abXcd"
*/
int main( int argc, char *argv[] )
{
char cary[CSIZE] = { 'a', 'b', 'c', 'd', 'e', EOS };
/*
| 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 |
cary|'a'|'b'|'c'|'d'|'e'|EOS| ? | ? | ? | ? |
cary[3] に 'X' を入れたい
そのためには、cary[3] を空き部屋にしたい
cary[4] 以後を移動する必要がある
cary|'a'|'b'|'c'| ? |'d'|'e'|EOS| ? | ? | ? |
[step 0]
cary[6] = EOS
cary[5] = 'e'
cary[4] = 'd'
[step 1]
cary[6] = cary[5]
cary[5] = cary[4]
cary[4] = cary[3]
[step 2]
i=5
cary[i+1] = cary[i]
i = i - 1
cary[i+1] = cary[i]
i = i - 1
cary[i+1] = cary[i]
i = i - 1
[step 3]
for ( i = 5; i >= 3; i-- ) {
cary[i+1] = cary[i]
}
この 5 は、実は元の文字列の長さ
変数 l にいれる
[step 3]
for ( i = l; i >= 3; i-- ) {
cary[i+1] = cary[i]
}
*/
int i;
int l;
printf ( "最初の cary = %s\n", cary );
/*
文字列 "abcde" の入った文字配列 cary の
3 文字目 ('c') と 4 文字目 'd' の間に、一文字 'X' を入れる
*/
/* 新しい文字列の長さを求める */
/* 変数 l に入れる */
for ( l = 0; cary[l] != EOS; l++ ) {
/* 中身の部分は空っぽでよい */
/* 変数 l の値を変更する事が目的 */
}
/* l には、元の文字列の長さが入る */
/* cary の中の文字列の長さは、変数 l に入る */
for ( i = l; 3 <= i; i-- ) { /* 後ろからコピーする必要がある */
/*
** この部分を完成させなさい
*/
}
/*
| 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 |
cary|'a'|'b'|'c'|'d'|'d'|'e'|EOS| ? | ? | ? | ? |
^
|
' X'
cary|'a'|'b'|'c'|'X'|'d'|'e'|EOS| ? | ? | ? | ? |
*/
cary[3] = 'X'; /* 空けた場所に 'X' を入れる */
/*
| 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 |
cary|'a'|'b'|'c'|'d'|'e'|EOS| ? | ? | ? | ? |
| | | \ \ \
cary|'a'|'b'|'c'|'X'|'d'|'e'|EOS| ? | ? | ? | ? |
*/
printf ( "'X' を挿入した結果 : %s\n", cary );
return 0;
}
/*
p-001.c : 構造体のデータを関数に渡す
*/
#define ARRAY_SIZE 1000
typedef struct {
int array[ARRAY_SIZE];
/*
int array0;
int array1;
..
int array999;
*/
} Array;
int add2 ( Array ary ) {
/* 配列を要素とする、構造体(を利用して作った型)のデータを渡す */
return ary.array[0] + ary.array[1];
}
int main(int argc, char *argv[] ) {
Array a;
printf ( "%d\n", add2( a ) );
}
/*
p-002.c : 配列のデータを関数に渡す
*/
#define ARRAY_SIZE 1000
int add2 ( int ary[ARRAY_SIZE] ) {
/* 配列を直接渡しているように見える */
return ary[0] + ary[1];
}
int main(int argc, char *argv[] ) {
int a[ARRAY_SIZE];
printf ( "%d\n", add2( a ) );
}
/*
機能的は、確かに、
p-001.c (構造体) と p-002.c (配列)
では、同じ
性能的には、ぜんぜん違う
p-001.c のほうは、構造体のサイズが大きくなると、時間がかかる
p-002.c のほうは、配列のサイズがおおきくなっても、時間は変化しない
*/
#include <stdio.h>
/*
データを組み合わせて、複雑な構造を持つデータ作る仕組み
構造体 : 異なる型(対象が同じなら同じ型)のものをまとめる
配列 : 同じ型のものまとめる
構造体:
typedef を利用して、新しい型が作れる
# 構造体は、型を作る仕組みとだけ利用する
配列:
同じ型を組み合わせただけけでなく、そのまま変数に利用する
*/
typedef struct {
int age; /* 年齢 */
char *name; /* 名前 */
char *address; /* 住所 */
} Person; /* 個人情報 */
int main(int argc, char *argv[]) {
Person kurino = { 0, "栗野俊一", "??" };
/* 構造体を使っているが、typedef 経由なので表にでない */
Person room2016[60] = {
/* 学籍番号 1 */ { 19, "赤木..", "?? },
/* 学籍番号 2 */ { 19, "伊藤..", "?? },
...
};
/* 配列は、直接現れている */
/*
typedef Person Romm[60];
Room room2016;
と、typedef 経由で型定義をする事はできるのだが..
C 言語では、あまりしない
*/
}
#include <stdio.h>
int sub ( int ary[100] ) {
/* ????(????) ary ??A?z??????U???? */
return ary[0] + ary[1];
}
int main(int argc, char *argv[] ) {
int ary[100] = { 1, 2, };
printf ( "%d\n", sub ( ary ) );
/* ?z?? ?uary?v???????w???鎖??????? */
/* ??????????A
?l(????????????A?????l???v?Z?????)???w????B
??????????A????l???R?s?[?????
=> ary ????l??????
*/
return 0;
}
#include <stdio.h>
void sub ( int a[100] ) {
printf ( "a=%p\n", a );
printf ( "a[0]=%d\n", a[0] );
printf ( "a[1]=%d\n", a[1] );
}
int main(int argc, char *argv[] ) {
int ary1[100] = { 1, 2, };
int ary2[100] = { 100, 200, };
printf ( "ary1=%p\n", ary1 );
/* ?z?? ary1 ???u?l?v?????? */
printf ( "ary2=%p\n", ary2 );
sub ( ary1 );
sub ( ary2 );
return 0;
}
/*
?z?? : ??????????????????
??????????u?????v?L?^?????????
int ary[10];
ary[0], ary[1], .., ary[9]
+-----------+
| ary[0] | ?z?????A??????????
+-----------+
| ary[1] | ?c??????A?v?Z???????A?w???????
+-----------+
| ...... |
+-----------+
| ary[9] |
+-----------+
*/
#include <stdio.h>
void sub ( char *str ) {
printf ( "str の最初の文字は %c\n", *str );
/*
文字列には、頭に * をつけると、先頭の文字が取り出せる
*/
printf ( "str の最初の文字は %c\n", str[0] );
printf ( "str の次の文字は %c\n", str[1] );
/*
str[n] == *(str + n)
*/
}
int main(int argc, char *argv[]) {
sub ( "abc" );
/* 文字列を関数に渡すことができる */
return 0;
}
void sub ( char *str ) {
printf ( "%s\n", str );
printf ( "%c\n", str[0] ); /* *(str+0) */
printf ( "%p\n", str );
}
int main(int argc, char *argv[]) {
char ary[4] = { 'a', 'b', 'c', '\0' };
/*
ary[4]
+------+
ary[0] | 'a' | 先頭の場所がわかれば、次は計算できる
+------+
ary[1] | 'b' |
+------+
ary[2] | 'c' |
+------+
ary[3] | '\0 |
+------+
*/
sub ( "abc" );
/* 文字列を関数に渡すことができる */
sub ( ary );
ary[0] = 'A';
sub ( ary );
return 0;
}
/*
配列名は、
配列が記録されている「場所を表す情報(ポインター値)」
をもっていて、それを関数の引数として渡すことができる
ポインター値を利用すると
その場所にある(変数の)情報を、参照したり、変更する事ができる
*/
/*
型のサイズ
その型の値を保存する変数がメモリ内に占める大きさ[byte 数](what:定義)
例
char -> 1 ( byte )
int -> ? ( byte ) : そのコンピュータに都合が良い数のサイズ
コンピュータによって異なったり、
あるいは、C コンパイラによって異なることもある
C 言語の int は、そのコンピュータでもっとも効率のよい計算をする
利点:効率の良いプログラムになる
C 言語のプログラムは同じプログラムが、
欠点:システムによって、異なる振る舞いをする可能性がある
プログラム内で、サイズを知る方法が与えられている
それを利用して(必要なら)、欠点を補う
sizeof
*/
#include <stdio.h>
int main(int argc, char *argv[]) {
printf ( "sizeof(char) = %d\n", sizeof(char) );
printf ( "sizeof(int) = %d\n", sizeof(int) );
printf ( "sizeof(double) = %d\n", sizeof(double) );
return 0;
}