ThinkPlus USBトラベルキーボードウルトラナビ付を購入した。
RealForceとかHHKの方がキーボードとしては良いのだけど、トラックポイントの便利さと値段の都合でこっちにしてみた。これで机の上からマウスを排除出来る。
しかし、このキーボードにはトラックポイントの無いキーボードを使えなくするという恐ろしい罠があるらしく、実際使えなくなった。一生Lenovoに金を払い続ける事になりそう。(因みに、このキーボードは持ち歩く事を前提に作られているので、家以外でも使える。技術教室に持ち込んだらかなり浮いたけど……。)
トラックポイントキャップは、3種類使ってみて一番思い通りに動かせたクラシックドームを使っている。但し、すぐ使えなくなるので予備として幾つか用意しておく必要がある。
マウスが邪魔だと思ってる人とかキーボードから手を離したくない人にお奨め。
2進数,8進数,16進数を実装。
#include <stdio.h>
#include <stdlib.h>
#define isBin(data) ((data&0xFE) == 0x30)
#define isOct(data) ((data&0xF8) == 0x30)
#define isDec(data) ('0' <= data & data <= '9')
#define isHex(data) (isDec(data) | 'A' <= (data&0xDF) & (data&0xDF) <= 'F')
typedef struct token_list
{
struct token_list *prev;
struct token_list *next;
char *token;
} token_list_t;
token_list_t *push_token(token_list_t *token_list,char *token)
{
if(!token_list){
token_list = (token_list_t *)calloc(1,sizeof(token_list_t));
if(!token_list){
return NULL;
}
}
else{
while(token_list->next){
token_list = token_list->next;
}
token_list->next = (token_list_t *)calloc(1,sizeof(token_list_t));
if(!token_list->next){
return NULL;
}
token_list->next->prev = token_list;
token_list = token_list->next;
}
token_list->token = token;
return token_list;
}
token_list_t *lexer(FILE *input)
{
token_list_t *token_list = NULL;
int getf;
char *token;
while(1){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(feof(input) || getf == '\0'){
break;
}
switch(getf){
case ' ':
case '\t':
case '\r':
case '\n':
break;
case '*':
case '%':
case '~':
case '^':
case ',':
case '(':
case ')':
case '[':
case ']':
token = (char *)malloc(16);
*token = getf;
*(token+1) = '\0';
token_list = push_token(token_list,token);
break;
case '+':
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '+';
getf = fgetc(input);
if(getf == '+'){
*(token+1) = '+';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
break;
case '-':
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '-';
getf = fgetc(input);
if(getf == '-'){
*(token+1) = '-';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
break;
case '/':
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(getf == '*'){
while(1){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(feof(input)){
return NULL;
}
if(getf == '*'){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(getf == '/'){
break;
}
else{
ungetc(getf,input);
}
}
}
}
else{
ungetc(getf,input);
token = (char *)malloc(16);
*token = '/';
*(token+1) = '\0';
token_list = push_token(token_list,token);
}
break;
case '=':
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '=';
getf = fgetc(input);
if(getf == '='){
*(token+1) = '=';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
break;
case '>':
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '>';
getf = fgetc(input);
if(getf == '='){
*(token+1) = '=';
*(token+2) = '\0';
}
else if(getf == '>'){
*(token+1) = '>';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
break;
case '<':
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '<';
getf = fgetc(input);
if(getf == '='){
*(token+1) = '=';
*(token+2) = '\0';
}
else if(getf == '<'){
*(token+1) = '<';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
break;
case '!':
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '!';
getf = fgetc(input);
if(getf == '='){
*(token+1) = '=';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
break;
case '&':
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '&';
getf = fgetc(input);
if(getf == '&'){
*(token+1) = '&';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
break;
case '|':
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '|';
getf = fgetc(input);
if(getf == '|'){
*(token+1) = '|';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
break;
default:
if(getf == '0'){
int f_flag = 0;
int count = 2;
token = (char *)malloc(16);
*token = '0';
*(token+1) = '\0';
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
switch(getf){
case 'x':
case 'X':
count++;
*(token+1) = getf;
*(token+2) = '\0';
while(1){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(isHex(getf)){
if(!(count&15)){
token = (char *)realloc(token,count+16);
}
count++;
*(token+count-2) = getf;
*(token+count-1) = '\0';
}
else{
if(count == 3){
return NULL;
}
ungetc(getf,input);
token_list = push_token(token_list,token);
break;
}
}
break;
case 'o':
case 'O':
count++;
*(token+1) = getf;
*(token+2) = '\0';
while(1){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(isOct(getf)){
if(!(count&15)){
token = (char *)realloc(token,count+16);
}
count++;
*(token+count-2) = getf;
*(token+count-1) = '\0';
}
else{
if(count == 3){
return NULL;
}
ungetc(getf,input);
token_list = push_token(token_list,token);
break;
}
}
break;
case 'b':
case 'B':
count++;
*(token+1) = getf;
*(token+2) = '\0';
while(1){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(isBin(getf)){
if(!(count&15)){
token = (char *)realloc(token,count+16);
}
count++;
*(token+count-2) = getf;
*(token+count-1) = '\0';
}
else{
if(count == 3){
return NULL;
}
ungetc(getf,input);
token_list = push_token(token_list,token);
break;
}
}
break;
default:
ungetc(getf,input);
while(1){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(isDec(getf) || (getf == '.' && !f_flag)){
if(!(count&15)){
token = (char *)realloc(token,count+16);
}
if(getf == '.'){
f_flag = 1;
}
count++;
*(token+count-2) = getf;
*(token+count-1) = '\0';
}
else{
ungetc(getf,input);
token_list = push_token(token_list,token);
break;
}
}
}
}
else if(isDec(getf) || getf == '.'){
int f_flag = 0;
int count = 1;
ungetc(getf,input);
token = (char *)malloc(16);
while(1){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(isDec(getf) || (getf == '.' && !f_flag)){
if(!(count&15)){
token = (char *)realloc(token,count+16);
}
if(getf == '.'){
f_flag = 1;
}
count++;
*(token+count-2) = getf;
*(token+count-1) = '\0';
}
else{
if(*token == '.' && *(token+1) == '\0'){
return NULL;
}
ungetc(getf,input);
token_list = push_token(token_list,token);
break;
}
}
}
else{
return NULL;
}
}
}
if(token_list){
while(token_list->prev){
token_list = token_list->prev;
}
}
return token_list;
}
int main(int argc,char **argv)
{
token_list_t *token_list = lexer(stdin);
if(token_list == NULL){
fputs("Error!\n",stdout);
return 0;
}
while(1){
fputs(token_list->token,stdout);
fputs("\n",stdout);
if(token_list->next){
token_list = token_list->next;
}
else{
break;
}
}
return 0;
}
現時点では使い道が良く分からない何かでしかないけど、そのうち或る程度まともに使える言語を作る予定。とりあえず字句解析器を公開する。
#include <stdio.h>
#include <stdlib.h>
typedef struct token_list
{
struct token_list *prev;
struct token_list *next;
char *token;
} token_list_t;
token_list_t *push_token(token_list_t *token_list,char *token)
{
if(!token_list){
token_list = (token_list_t *)calloc(1,sizeof(token_list_t));
if(!token_list){
return NULL;
}
}
else{
while(token_list->next){
token_list = token_list->next;
}
token_list->next = (token_list_t *)calloc(1,sizeof(token_list_t));
if(!token_list->next){
return NULL;
}
token_list->next->prev = token_list;
token_list = token_list->next;
}
token_list->token = token;
return token_list;
}
token_list_t *lex(FILE *input)
{
token_list_t *token_list = NULL;
int getf;
char *token;
while(1){
token = NULL;
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(feof(input)){
break;
}
else{
/*
演算子とか
*/
if(getf == '*' || getf == '%' || getf == '~' || getf == '^' || getf == ',' || getf == '(' || getf == ')' || getf == '[' || getf == ']'){
token = (char *)malloc(16);
*token = getf;
*(token+1) = '\0';
token_list = push_token(token_list,token);
}
else if(getf == '+'){
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '+';
getf = fgetc(input);
if(getf == '+'){
*(token+1) = '+';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
}
else if(getf == '-'){
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '-';
getf = fgetc(input);
if(getf == '-'){
*(token+1) = '-';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
}
else if(getf == '/'){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(getf == '*'){
while(1){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(feof(input)){
return NULL;
}
if(getf == '*'){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(getf == '/'){
break;
}
else{
ungetc(getf,input);
}
}
}
}
else{
ungetc(getf,input);
token = (char *)malloc(16);
*token = '/';
*(token+1) = '\0';
token_list = push_token(token_list,token);
}
}
else if(getf == '='){
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '=';
getf = fgetc(input);
if(getf == '='){
*(token+1) = '=';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
}
else if(getf == '>'){
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '>';
getf = fgetc(input);
if(getf == '='){
*(token+1) = '=';
*(token+2) = '\0';
}
else if(getf == '>'){
*(token+1) = '>';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
}
else if(getf == '<'){
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '<';
getf = fgetc(input);
if(getf == '='){
*(token+1) = '=';
*(token+2) = '\0';
}
else if(getf == '<'){
*(token+1) = '<';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
}
else if(getf == '!'){
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '!';
getf = fgetc(input);
if(getf == '='){
*(token+1) = '=';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
}
else if(getf == '&'){
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '&';
getf = fgetc(input);
if(getf == '&'){
*(token+1) = '&';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
}
else if(getf == '|'){
if(ferror(input)){
return NULL;
}
token = (char *)malloc(16);
*token = '|';
getf = fgetc(input);
if(getf == '|'){
*(token+1) = '|';
*(token+2) = '\0';
}
else{
*(token+1) = '\0';
ungetc(getf,input);
}
token_list = push_token(token_list,token);
}
/*数値*/
else if('0' <= getf && getf <= '9' || getf == '.'){
int f_flag = 0;
int count = 1;
ungetc(getf,input);
token = (char *)malloc(16);
while(1){
if(ferror(input)){
return NULL;
}
getf = fgetc(input);
if(('0' <= getf && getf <= '9') || (getf == '.' && !f_flag)){
if(getf == '.'){
f_flag = 1;
}
count++;
if(!(count&15)){
token = (char *)realloc(token,count+16);
}
*(token+count-2) = getf;
*(token+count-1) = '\0';
}
else{
ungetc(getf,input);
token_list = push_token(token_list,token);
break;
}
}
}
/*不正な文字*/
else if(getf != ' ' && getf != '\t' && getf != '\r' && getf != '\n'){
return NULL;
}
}
}
if(token_list){
while(token_list->prev){
token_list = token_list->prev;
}
}
return token_list;
}
新年の挨拶だけ書いても面白くないと思うのでコミケの行動記録を書いてみる。
サークル入場の前に、或る人に頼んでおいたC73 Keyセットと頼まれている幺樂団の歴史4,幺樂団の歴史5の分のお金(+お年玉)を受け取った。
Neetpiaのスペースに5人くらいで固まっていたら狭かったので半分追い出されるような形で上海アリス幻樂団の列に並んだ。
10時。ZUNさんが偽ビールジョッキを持って「乾杯!」と言う今までで一番印象に残ったコミケ開場の瞬間でした。
幺樂団の歴史4,幺樂団の歴史5を6部ずつ確保。
もりやマ!!を買い、Spring Fieldを貰った。
西1に移動。どこから行けば良いのか分からなくて焦った。
幺樂団の歴史4,幺樂団の歴史5を頼まれた人とは別の人に同人ゲームとかを幾つか頼まれていたので、全部確保。西-れ43ab「ロケット野郎」の新刊を後回しにしたのは何か間違ってると思う。買えたけど。
サークルから出たお金で同人STGを幾つか購入。
何故かサークル会議。今後の予定とかについて色々。
西2の外でCDが大量に積まれているのを見た。(謎)
有明から脱出。結局東には行かなかった。
明けましておめでとう御座います。