ページ 1 / 1
C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月12日(月) 18:21
by fabersid
formのgetで送信しhtmlのidを取得したい
idの内容例
<span id="result_box" class="short_text" lang="ja"><span class="">こんにちは</span><br><span>こんにちは</span></span>
↑ "short_text"は固定ではない
表示内容は br タグ以外を除いた
こんにちは
こんにちは
です。
入力ファイルを1行ずつ取り込みhttps://translate.google.co.jp/?client=#en/ja/文字列
という風にして送り、id="result_box"からタグを消して出力ファイルに出力したいです。
一応、ファイルの入出力だけはできています。
コード:
/* header files */
#include <stdio.h>
#include <stdlib.h>
/* macros */
#define N 256
/* main */
int main(void) {
FILE *fp;
char *filename = "readme.txt";
char readline[N] = {'\0'};
/* ファイルのオープン */
if ((fp = fopen(filename, "r")) == NULL) {
fprintf(stderr, "%sのオープンに失敗しました.\n", filename);
exit(EXIT_FAILURE);
}
/* ファイルの終端まで文字を読み取り表示する */
while ( fgets(readline, N, fp) != NULL ) {
//https://translate.google.co.jp/?client=#en/ja/翻訳元
//id : result_box
printf("%s", readline);
}
/* ファイルのクローズ */
fclose(fp);
return 0;
}
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月13日(火) 00:12
by かずま
OS やコンパイラなどの環境を書いてほしいですね。
Windows でこんなコードを書いてみました。
コード:
#include <stdio.h> // fopen, fclose, fgets, printf, sscanf, sprintf, remove
#include <stdlib.h> // system
#include <string.h> // strstr
#define N 256
#define M 128
char *filename = "readme.txt";
char *tempname = "tmp12345.txt";
char buf[1024*1024];
void find_line(const char *str)
{
FILE *fp = fopen(tempname, "r");
if (!fp) return;
while (fgets(buf, sizeof buf, fp)) {
char *p = strstr(buf, str);
if (p) printf("%.*s\n", M, p-9);
}
fclose(fp);
}
int main(void)
{
char readline[N];
FILE *fp = fopen(filename, "r");
if (fp == NULL) {
fprintf(stderr, "can't open %s\n", filename);
return 1;
}
while (fgets(readline, N, fp)) {
char word[N], cmd[N + 200];
printf("%s", readline);
sscanf(word, "%s", readline);
sprintf(cmd, "powershell -command invoke-webrequest -uri https:"
"//translate.google.co.jp/?client=#en/ja/%s -outfile %s",
word, tempname);
system(cmd);
find_line("result_box");
}
fclose(fp);
remove(tempname);
return 0;
}
readme.txt
実行結果
コード:
hello
<span id=result_box class="short_text"></span></div></div><div id="gt-edit" style="display:none"><div style="width: 100%;"><text
「こんにちは」を含む結果を得られませんでしたが、
少しは参考になるかもしれません。
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月13日(火) 21:53
by fabersid
OS:Microsoft Windows 10 64bit
コンパイラ:bcc32
Windows PowerShellはありますが、cmd.exeのコマンドしか
標準のスクリプトは動かしていないのでよくわからないので調べておきます。
このトピックは期待する出力結果が導けるまで続けるつもりです。
期待される値:<span class="short_text" id="result_box" lang="ja"><span>こんにちは</span></span>
今回:
hello
<span id=result_box class="short_text"></span></div></div><div id="gt-edit" style="display:none"><div style="width: 100%;"><text
翻訳結果が反映される前にHTMLを取得したものと思われる
(極端な例:上限である5000字を翻訳した場合、結果が遅れて表示される場合がある。)
[table=][tr=][td=]GETリクエストの送信[/td][td=]OK[/td][/tr]
[tr=][td=]HTMLの取得(答えを含まない)[/td][td=]OK[/td][/tr]
[tr=][td=]HTMLの取得(答えを含んだ)[/td][td=][/td][/tr]
[tr=][td=]HTMLの取得(outerHTML)[/td][td=][/td][/tr]
[tr=][td=]HTMLの取得(innerHTML)[/td][td=][/td][/tr]
[tr=][td=]HTMLタグの除去[/td][td=][/td][/tr][/table]
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月15日(木) 02:18
by かずま
sscanf の引数が間違っていました。
また、"?#en/ja/hello" ではだめなようなので、
"oe=cp932&text=hello" にしました。
コード:
#include <stdio.h> // fopen, fclose, fgets, printf, sscanf, sprintf, remove
#include <stdlib.h> // system
#include <string.h> // strstr, strchr
#define N 256
char *filename = "readme.txt";
char *tempname = "tmp12345.txt";
char buf[1024*1024];
void find_line(const char *str)
{
FILE *fp = fopen(tempname, "r");
if (!fp) return;
while (fgets(buf, sizeof buf, fp)) {
char *p = strstr(buf, str);
if (p) {
p = strchr(strchr(p, '>') + 1, '>') + 1;
*strchr(p, '<') = '\0';
printf("[%s]\n", p);
}
}
fclose(fp);
}
int main(void)
{
char readline[N];
FILE *fp = fopen(filename, "r");
if (fp == NULL) {
fprintf(stderr, "can't open %s\n", filename);
return 1;
}
while (fgets(readline, N, fp)) {
char word[N], cmd[N + 200];
sscanf(readline, "%s", word);
puts(word);
sprintf(cmd, "powershell -command invoke-webrequest -uri https:"
"//translate.google.co.jp/?oe=cp932\"\"\"&\"\"\"text=%s"
" -outfile %s", word, tempname);
system(cmd);
find_line("<span id=result_box");
}
fclose(fp);
remove(tempname);
return 0;
}
readme.txt
実行結果
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月15日(木) 02:54
by かずま
good morning のようにスペースを含む文字列でもよいようにしてみました。
コード:
while (fgets(readline, N, fp)) {
char word[N + 100], cmd[N + 300], *p = word, *q = readline, c;
while ((c = *q++) && c != '\n')
if (c == ' ') strcpy(p, "%20"), p += 3;
else *p++ = c;
*p = '\0';
sprintf(cmd, "powershell -command invoke-webrequest -uri https:"
"//translate.google.co.jp/?oe=cp932\"\"\"&\"\"\"text=%s"
" -outfile %s", word, tempname);
system(cmd);
find_line("<span id=result_box");
}
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月15日(木) 14:56
by fabersid
コード:
while ((c = *q++) && c != '\n')
にて
bcc32 google_translate(Line_by_line).c
Borland C++ 5.5.1 for Win32 Copyright (c) 1993, 2000 Borland
google_translate(Line_by_line).c:
警告 W8060 google_translate(Line_by_line).c 36: おそ らく不正な代入(関数 main )
Turbo Incremental Link 5.00 Copyright (c) 1997, 2000 Borland
のような警告があった以外問題ないと思ったのですが、
コード:
Invoke-WebRequest : パラメーター 'Uri' で必要とされる型 'System.Uri' に 'Sys
tem.Object[]' を変換できません。指定されたメソッドはサポートされていません。
発生場所 行:1 文字:24
+ ... equest -uri https://translate.google.co.jp/?oe=cp932"&"text=Please%20
...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidArgument: (:) [Invoke-WebRequest]、Para
meterBindingException
+ FullyQualifiedErrorId : CannotConvertArgument,Microsoft.PowerShell.Co
mmands.InvokeWebRequestCommand
コード:
文字列に終端記号 ' がありません。
+ CategoryInfo : ParserError: (:) [], ParentContainsErrorRecor
dException
+ FullyQualifiedErrorId : TerminatorExpectedAtEndOfString
というエラーがありました。
今回テストに使ったreadme.txt
► スポイラーを表示
コード:
Project Title
One Paragraph of project description goes here
Getting Started
These instructions will get you a copy of the project up and running on your local machine for development and testing purposes. See deployment for notes on how to deploy the project on a live system.
Prerequisites
What things you need to install the software and how to install them
Give examples
Installing
A step by step series of examples that tell you have to get a development env running
Say what the step will be
Give the example
And repeat
until finished
End with an example of getting some data out of the system or using it for a little demo
Running the tests
Explain how to run the automated tests for this system
Break down into end to end tests
Explain what these tests test and why
Give an example
And coding style tests
Explain what these tests test and why
Give an example
Deployment
Add additional notes about how to deploy this on a live system
Built With
Dropwizard - The web framework used
Maven - Dependency Management
ROME - Used to generate RSS Feeds
Contributing
Please read CONTRIBUTING.md for details on our code of conduct, and the process for submitting pull requests to us.
Versioning
We use SemVer for versioning. For the versions available, see the tags on this repository.
Authors
Billie Thompson - Initial work - PurpleBooth
See also the list of contributors who participated in this project.
License
This project is licensed under the MIT License - see the LICENSE.md file for details
Acknowledgments
Hat tip to anyone who's code was used
Inspiration
etc
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月15日(木) 15:20
by かずま
bcc32 で警告が出ないようにしました。
コード:
#include <stdio.h> // fopen, fclose, fgets, printf, sscanf, sprintf, remove
#include <stdlib.h> // system
#include <string.h> // strstr, strchr
#define N 256
char *filename = "readme.txt";
char *tempname = "tmp12345.txt";
char buf[1024*1024];
void find_line(const char *str)
{
FILE *fp = fopen(tempname, "r");
if (!fp) return;
while (fgets(buf, sizeof buf, fp)) {
char *p = strstr(buf, str);
if (p) {
p = strchr(strchr(p, '>') + 1, '>') + 1;
*strchr(p, '<') = '\0';
printf(" -> [%s]\n", p);
}
}
fclose(fp);
}
int main(void)
{
char readline[N];
FILE *fp = fopen(filename, "r");
if (!fp) { fprintf(stderr, "can't open %s\n", filename); return 1; }
while (fgets(readline, N, fp)) {
char word[N + 100], cmd[N + 300], *p = word, *q = readline, c;
printf("%s", readline);
while ((c = *q++) != '\0' && c != '\n')
(c == ' ') ? (*p++ = '%', *p++ = '2', *p++ = '0') : (*p++ = c);
*p = '\0';
sprintf(cmd, "powershell -command wget \"\"\"https:"
"//translate.google.co.jp/?oe=cp932&text=%s\"\"\""
" -outfile %s", word, tempname);
system(cmd);
find_line("<span id=result_box");
}
fclose(fp);
remove(tempname);
return 0;
}
実行結果
コード:
Project Title
-> [プロジェクト名]
One Paragraph of project description goes here
-> [プロジェクト記述の1段落はここに]
Getting Started
-> [入門]
These instructions will get you a copy of the project up and running on your local machine for development and testing purposes. See deployment for notes on how to deploy the project on a live system.
-> [これらの手順では、開発とテストの目的でローカルマシン上でプロジェクトのコピーを作成して実行します。]
Prerequisites
-> [前提条件]
What things you need to install the software and how to install them
-> [ソフトウェアのインストールに必要なものとソフトウェアのインストール方法]
Give examples
-> [例を上げてください]
Installing
-> [インストール]
A step by step series of examples that tell you have to get a development env running
-> [開発環境を実行する必要があることを示すステップバイステップの一連の例]
Say what the step will be
-> [ステップが何であるかを言う]
Give the example
-> [例を挙げなさい]
And repeat
-> [繰り返し]
until finished
-> [終了するまで]
End with an example of getting some data out of the system or using it for a little demo
-> [いくつかのデータをシステムから取り出したり、小さなデモで使用したりする例で終わります]
Running the tests
-> [テストの実行]
Explain how to run the automated tests for this system
-> [このシステムの自動テストの実行方法を説明する]
Break down into end to end tests
-> [エンドツーエンドのテストに分割する]
Explain what these tests test and why
-> [これらのテストがテストする内容と理由]
Give an example
-> [例を挙げる]
And coding style tests
-> [そしてコーディングスタイルテスト]
Explain what these tests test and why
-> [これらのテストがテストする内容と理由]
Give an example
-> [例を挙げる]
Deployment
-> [配置]
Add additional notes about how to deploy this on a live system
-> [ライブシステムにこれをデプロイする方法に関する追加の注釈を追加する]
Built With
-> [で構築された]
Dropwizard - The web framework used
-> [Dropwizard - 使用されたWebフレームワーク]
Maven - Dependency Management
-> [Maven - 依存関係管理]
ROME - Used to generate RSS Feeds
-> [ROME - RSSフィードの生成に使用]
Contributing
-> [貢献する]
Please read CONTRIBUTING.md for details on our code of conduct, and the process for submitting pull requests to us.
-> [私たちの行動規範に関する詳細、およびプルリクエストを提出するプロセスについては、CONTRIBUTING.mdをご覧ください。]
Versioning
-> [バージョン管理]
We use SemVer for versioning. For the versions available, see the tags on this repository.
-> [バージョニングにはSemVerを使用します。]
Authors
-> [著者]
Billie Thompson - Initial work - PurpleBooth
-> [ビリー・トンプソン - 初期作品 - パープルブース]
See also the list of contributors who participated in this project.
-> [このプロジェクトに参加した貢献者のリストも参照してください。]
License
-> [ライセンス]
This project is licensed under the MIT License - see the LICENSE.md file for details
-> [このプロジェクトはMITライセンスの下でライセンスされています - 詳細はLICENSE.mdファイルを参照してください]
Acknowledgments
-> [謝辞]
Hat tip to anyone who's code was used
-> [コードが使用されている人の帽子]
Inspiration
-> [インスピレーション]
etc
-> [等]
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月15日(木) 15:48
by かずま
元のプログラムでダメだった原因が分かりました。
URI のうち「&」だけを「"」で囲んでいましたが、
text= のところに「,」があると、それが特別な
意味に解釈されていたようです。
新しいプログラムでは URI全体を「"」で囲んで
いるのでうまくいくみたいです。
スペースを %20 に変換する必要もないようなので、
次のように '\n' の削除だけにします。
コード:
while (fgets(readline, N, fp)) {
char cmd[N + 200], *p = strchr(readline, '\n');
if (p) *p = '\0';
sprintf(cmd, "powershell -command wget \"\"\"https:"
"//translate.google.co.jp/?oe=cp932&text=%s\"\"\""
" -outfile %s", readline, tempname);
system(cmd);
find_line("<span id=result_box");
}
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月15日(木) 16:23
by かずま
text の中に「&」や「"」があるとだめですね。
これでどうでしょうか?
コード:
while (fgets(readline, N, fp)) {
char word[N + 100], cmd[N + 300], *p = word, *q = readline, c;
while ((c = *q++) != '\0' && c != '\n')
if (c == '&' || c == '"') p += sprintf(p, "%%%02X", c);
else *p++ = c;
*p = '\0';
sprintf(cmd, "powershell -command wget \"\"\"https:"
"//translate.google.co.jp/?oe=cp932&text=%s\"\"\""
" -outfile %s", word, tempname);
system(cmd);
find_line("<span id=result_box");
}
今度は、翻訳結果の「"」が「"」になるのを
何とかしないといけませんね。
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月15日(木) 17:16
by fabersid
コード:
#include <stdio.h> // fopen, fclose, fgets, printf, sscanf, sprintf, remove
#include <stdlib.h> // system
#include <string.h> // strstr, strchr
#define N 256
void strchg(char *, const char *, const char *);
char *filename = "readme.txt";
char *tempname = "tmp12345.txt";
char buf[1024*1024];
void find_line(const char *str)
{
FILE *fp = fopen(tempname, "r");
if (!fp) return;
while (fgets(buf, sizeof buf, fp)) {
char *p = strstr(buf, str);
if (p) {
p = strchr(strchr(p, '>') + 1, '>') + 1;
*strchr(p, '<') = '\0';
strchg(p,"'","");//ここで"を削除
/*printf(" -> [%s]\n", p);*/printf("%s\n", p);
}
}
fclose(fp);
}
int main(void)
{
char readline[N];
FILE *fp = fopen(filename, "r");
if (!fp) { fprintf(stderr, "can't open %s\n", filename); return 1; }
while (fgets(readline, N, fp)) {
char word[N + 100], cmd[N + 300], *p = word, *q = readline, c;
//printf("%s", readline);
while ((c = *q++) != '\0' && c != '\n')
(c == ' ') ? (*p++ = '%', *p++ = '2', *p++ = '0') : (*p++ = c);
*p = '\0';
sprintf(cmd, "powershell -command wget \"\"\"https:"
"//translate.google.co.jp/?oe=cp932&text=%s\"\"\""
" -outfile %s", word, tempname);
system(cmd);
find_line("<span id=result_box");
}
fclose(fp);
remove(tempname);
return 0;
}
void strchg(char *buf, const char *str1, const char *str2){
//https://www.grapecity.com/tools/support/powernews/column/clang/049/page03.htmより
char tmp[1024 + 1];
char *p;
while ((p = strstr(buf, str1)) != NULL) {
/* 見つからなくなるまで繰り返す
pは旧文字列の先頭を指している */
*p = '\0'; /* 元の文字列を旧文字列の直前で区切って */
p += strlen(str1); /* ポインタを旧文字列の次の文字へ */
strcpy(tmp, p); /* 旧文字列から後を保存 */
strcat(buf, str2); /* 新文字列をその後につなぎ */
strcat(buf, tmp); /* さらに残りをつなぐ */
}
}
うまくいったと思いきや
コード:
Project Title
Getting Started
Prerequisites
Give examples
'Hello'
"Hello"
""
''
''&&#ལ#39
のようなコードで
コード:
プロジェクト名
入門
前提条件
例を上げてください
'こんにちは'
こんにちは
''
となる
”(")はどこに消えたのでしょうか?
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月15日(木) 17:48
by fabersid
No.10は返信を見る前に投稿しました。
コード:
#include <stdio.h> // fopen, fclose, fgets, printf, sscanf, sprintf, remove
#include <stdlib.h> // system
#include <string.h> // strstr, strchr
#define N 256
void find_line(const char *);
void strchg(char *, const char *, const char *);
char *filename = "readme.txt";
char *tempname = "tmp12345.txt";
char buf[1024*1024];
void find_line(const char *str)
{
FILE *fp = fopen(tempname, "r");
if (!fp) return;
while (fgets(buf, sizeof buf, fp)) {
char *p = strstr(buf, str);
if (p) {
p = strchr(strchr(p, '>') + 1, '>') + 1;
*strchr(p, '<') = '\0';
strchg(p,""","\"");
strchg(p,"'","'");
/*printf(" -> [%s]\n", p);*/printf("%s\n", p);
}
}
fclose(fp);
}
int main(void)
{
char readline[N];
FILE *fp = fopen(filename, "r");
if (!fp) { fprintf(stderr, "can't open %s\n", filename); return 1; }
while (fgets(readline, N, fp)) {
char word[N + 100], cmd[N + 300], *p = word, *q = readline, c;
while ((c = *q++) != '\0' && c != '\n')
if (c == '&' || c == '"') p += sprintf(p, "%%%02X", c);
else *p++ = c;
*p = '\0';
sprintf(cmd, "powershell -command wget \"\"\"https:"
"//translate.google.co.jp/?oe=cp932&text=%s\"\"\""
" -outfile %s", word, tempname);
system(cmd);
find_line("<span id=result_box");
}
fclose(fp);
remove(tempname);
return 0;
}
void strchg(char *buf, const char *str1, const char *str2){
//https://www.grapecity.com/tools/support/powernews/column/clang/049/page03.htmより
char tmp[1024 + 1];
char *p;
while ((p = strstr(buf, str1)) != NULL) {
/* 見つからなくなるまで繰り返す
pは旧文字列の先頭を指している */
*p = '\0'; /* 元の文字列を旧文字列の直前で区切って */
p += strlen(str1); /* ポインタを旧文字列の次の文字へ */
strcpy(tmp, p); /* 旧文字列から後を保存 */
strcat(buf, str2); /* 新文字列をその後につなぎ */
strcat(buf, tmp); /* さらに残りをつなぐ */
}
}
投稿内容を反映したらうまくいったのですが、
謎の訳が入りました。
コード:
Project Title
Getting Started
Prerequisites
Give examples
'Hello'
"Hello"
""
''
''&&#ལ#39
コード:
プロジェクト名
入門
前提条件
例を上げてください
'こんにちは'
"こんにちは"
""
''
そして、
「そして、」とは&の訳らしいです。
最後のデバッグ用コード''&&#ལ#39でエンコードしきれなかったようです。
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月15日(木) 18:26
by fabersid
現在のコード
コード:
#include <stdio.h> // fopen, fclose, fgets, printf, sscanf, sprintf, remove
#include <stdlib.h> // system
#include <string.h> // strstr, strchr
#define N 256
void find_line(const char *);
void strchg(char *, const char *, const char *);
char *filename = "readme.txt";
char *tempname = "tmp12345.txt";
char buf[1024*1024];
void find_line(const char *str)
{
FILE *fp = fopen(tempname, "r");
if (!fp) return;
while (fgets(buf, sizeof buf, fp)) {
char *p = strstr(buf, str);
if (p) {
p = strchr(strchr(p, '>') + 1, '>') + 1;
*strchr(p, '<') = '\0';
strchg(p,"&","&");
strchg(p,""","\"");
strchg(p,"'","'");
/*printf(" -> [%s]\n", p);*/printf("%s\n", p);
}
}
fclose(fp);
}
int main(void)
{
char readline[N];
FILE *fp = fopen(filename, "r");
if (!fp) { fprintf(stderr, "can't open %s\n", filename); return 1; }
while (fgets(readline, N, fp)) {
char word[N + 100], cmd[N + 300], *p = word, *q = readline, c;
while ((c = *q++) != '\0' && c != '\n')
if (c == '&' || c == '"' || c == '#') p += sprintf(p, "%%%02X", c);
else *p++ = c;
*p = '\0';
sprintf(cmd, "powershell -command wget \"\"\"https:"
"//translate.google.co.jp/?oe=cp932&text=%s\"\"\""
" -outfile %s", word, tempname);
system(cmd);
find_line("<span id=result_box");
}
fclose(fp);
remove(tempname);
return 0;
}
void strchg(char *buf, const char *str1, const char *str2){
//https://www.grapecity.com/tools/support/powernews/column/clang/049/page03.htmより
char tmp[1024 + 1];
char *p;
while ((p = strstr(buf, str1)) != NULL) {
/* 見つからなくなるまで繰り返す
pは旧文字列の先頭を指している */
*p = '\0'; /* 元の文字列を旧文字列の直前で区切って */
p += strlen(str1); /* ポインタを旧文字列の次の文字へ */
strcpy(tmp, p); /* 旧文字列から後を保存 */
strcat(buf, str2); /* 新文字列をその後につなぎ */
strcat(buf, tmp); /* さらに残りをつなぐ */
}
}
INPUT
コード:
Project Title
''&&#ལ#39
"Hello"
'Hello'
OUTPUT
コード:
プロジェクト名
&#3939;#39
"こんにちは"
'こんにちは'
なぜか&と#が全角
Google 翻訳の仕様なので無視するべきか.....
翻訳は一応できるようになりました。
文が途中で切れていた時
不自然な訳になるという問題があります。
例えば
コード:
the 15th of March
the
15th
of
March
であれば
となり意味が不自然です。
文の終わり(="." && !='\0')を判断する方法がわかればさらに精度がよくなると思います。
中には説明に"."を使わない人もいるので難しい。
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月15日(木) 20:20
by fabersid
今更なのですが、
char *tempname = "tmp12345.txt";
をtmpnamで可変にしてほしいです。
私がやるとTMP1.$が作成されprintf("%s",tempname);ではTMP1.$$$が
出力されよくわかりません(別のトピックを立てたほうがいいのであればご指摘ください)。
関連せいの別せい トピック
Posted: 2018年2月15日(木) 21:51
by fabersid
tempfileに関する別のトピックと立てました。
何かがおかしいtmpfile
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月16日(金) 12:15
by fabersid
新たな不具合を発見
コード:
1. Start the debug
It's PDCA.
Plan
Do
Check
Act
------------------------------
のようなreadme.txtがあったとしたら5,7,9,11行目のようなスペースから始まる
文が翻訳できません。
今のコード(長いからスポイラーテキスト)
► スポイラーを表示
コード:
#include <stdio.h> // fopen, fclose, fgets, printf, sscanf, sprintf, remove
#include <stdlib.h> // system
#include <string.h> // strstr, strchr
#define N 256
void find_line(const char *);
void strchg(char *, const char *, const char *);
char *filename = "readme.txt";
char tempname[16];
char buf[1024*1024];
int main(void){
char readline[N];
FILE *fp = fopen(filename, "r");
if (!fp) { fprintf(stderr, "can't open %s\n", filename); return 1; }
tmpnam(tempname);
if(system("ping translate.google.co.jp>nul")!=0){
printf("通信エラー:Google 翻訳に接続できません。\n");
return 1;
}
while (fgets(readline, N, fp)) {
char word[N + 100], cmd[N + 300], *p = word, *q = readline, c;
while ((c = *q++) != '\0' && c != '\n')
if (c == '&' || c == '"' || c == '#' || c == ' ') p += sprintf(p, "%%%02X", c);
else *p++ = c;
*p = '\0';
if(strlen(word)==0){
printf("\n");
}else{
sprintf(cmd, "powershell -command wget \"\"\"https:"
"//translate.google.co.jp/?oe=cp932&text=%s\"\"\""
" -outfile '%s'", word, tempname);
system(cmd);
find_line("<span id=result_box");//printf("%s",cmd);
}
}
fclose(fp);
remove(tempname);
return 0;
}
void find_line(const char *str)
{
FILE *fp = fopen(tempname, "r");
if (!fp) return;
while (fgets(buf, sizeof buf, fp)) {
char *p = strstr(buf, str);
if (p) {
p = strchr(strchr(p, '>') + 1, '>') + 1;
*strchr(p, '<') = '\0';
strchg(p,"&","&");
strchg(p,""","\"");
strchg(p,"'","'");
strchg(p," "," ");
strchg(p,"&","&");
strchg(p,"#","#");
/*printf(" -> [%s]\n", p);*/printf("%s\n", p);
}
}
fclose(fp);
}
void strchg(char *buf, const char *str1, const char *str2){
//https://www.grapecity.com/tools/support/powernews/column/clang/049/page03.htmより
char tmp[1024 + 1];
char *p;
while ((p = strstr(buf, str1)) != NULL) {
/* 見つからなくなるまで繰り返す
pは旧文字列の先頭を指している */
*p = '\0'; /* 元の文字列を旧文字列の直前で区切って */
p += strlen(str1); /* ポインタを旧文字列の次の文字へ */
strcpy(tmp, p); /* 旧文字列から後を保存 */
strcat(buf, str2); /* 新文字列をその後につなぎ */
strcat(buf, tmp); /* さらに残りをつなぐ */
}
}
仮に先頭のスペースを無視するようにsystem(cmd);をしても
体裁が崩れ読みにくいものになります。
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月16日(金) 14:46
by かずま
先頭のスペースを数えておき、そのスペースを除いた翻訳結果を得て、
表示の時にスペースを復元すればよいのではありませんか?
コード:
#include <stdio.h> // fopen, fclose, fgets, printf, sscanf, sprintf, remove, tmpnam
#include <stdlib.h> // system
#include <string.h> // strstr, strchr, memcpy, memmove
#define N 256
void find_line(int);
void strchg(char *, const char *, const char *);
char *filename = "readme.txt";
char tempname[256];
char buf[1024*1024];
int main(void)
{
char readline[N];
FILE *fp = fopen(filename, "r");
if (!fp) return fprintf(stderr, "can't open %s\n", filename), 1;
tmpnam(tempname);
if (system("ping translate.google.co.jp>nul"))
return printf("通信エラー:Google 翻訳に接続できません。\n"), 1;
while (fgets(readline, N, fp)) {
int nspace;
char word[N + 100], cmd[N + 300], *p = word, *q = readline, c;
while (*q == ' ') q++;
nspace = q - readline;
while ((c = *q++) != '\0' && c != '\n')
if (strchr(" \"#&+", c)) p += sprintf(p, "%%%02X", c);
else *p++ = c;
*p = '\0';
if (*word) {
sprintf(cmd, "powershell -command wget \"\"\"https:"
"//translate.google.co.jp/?oe=cp932&text=%s\"\"\""
" -outfile '%s'", word, tempname);
system(cmd);
find_line(nspace);
}
else putchar('\n');
}
fclose(fp);
remove(tempname);
return 0;
}
void find_line(int nspace)
{
FILE *fp = fopen(tempname, "r");
if (!fp) return;
while (fgets(buf, sizeof buf, fp)) {
char *p = strstr(buf, "<span id=result_box");
if (p) {
p = strchr(strchr(p, '>') + 1, '>') + 1;
*strchr(p, '<') = '\0';
strchg(p,"&", "&");
strchg(p,""", "\"");
strchg(p,"'", "'");
strchg(p," ", " ");
strchg(p,"&", "&");
strchg(p,"#", "#");
printf("%*s%s\n", nspace, "", p);
}
}
fclose(fp);
}
void strchg(char *buf, const char *str1, const char *str2)
{
char *p = strstr(buf, str1);
if (p) {
int len = strlen(p) + 1, len1 = strlen(str1), len2 = strlen(str2);
do {
len -= p - buf + len1;
buf = p + len2;
memmove(buf, p + len1, len);
memcpy(p, str2, len2);
} while ((p = strstr(buf, str1)) != NULL);
}
}
Re: C言語とインターネットのサービスを連携させる方法
Posted: 2018年2月16日(金) 16:28
by かずま
かずま さんが書きました:
コード:
int len = strlen(p) + 1, len1 = strlen(str1), len2 = strlen(str2);
勝手に strchg を変更してすみません。
バグがありました。次のように訂正します。
コード:
int len = strlen(buf) + 1, len1 = strlen(str1), len2 = strlen(str2);