トップページ⇒php
1001コメント350KB

【Perl】初心者コーナー Part19

レス数が950を超えています。1000を超えると書き込みができなくなります。
0001nobodyさん03/01/11 13:52ID:???
初めに→「perl」その物のスレです。

1:自分はこう言う事がしたい。
2:それでこんな風にやってみたが・・・
3:それだとこんなエラーが出て上手く行かなかった。

1と3が無いと誰も答えられないよ。
良い回答は良い質問から。一緒に勉強しましょう。

あとは>>2-10にまかせた。
0877nobodyさん03/02/04 00:36ID:???
open(IN, 'master');
open(OUT, '>master.tmp');
while (IN) {
 if () {
  print OUT 新しいもの;
 } else {
  print OUT $_;
 }
}
rename('master.tmp', 'master');
0878nobodyさん03/02/04 00:37ID:???
>>876
死ねクソマルチ。 
0879nobodyさん03/02/04 00:38ID:???
>>876
マルチするほどの事じゃないだろ。どうせ見るヤツかぶってるんだし。

100行くらいならメモリに入れておいてもいいんじゃない?
メモリの量が気になるなら読み込みつつ別ファイルに書き込み。
マッチしたらその行だけ変更して最後まで読み書きする。
最後にリネームして終わりだな。

つか今度マルチしたらグーで殴るからね
0880nobodyさん03/02/04 00:39ID:???
>>875
utf8
0881nobodyさん03/02/04 01:02ID:Z72oZy+O
printの中で変数を展開したいのですが、どうすればいいのですか?

$i = 1;
print "$i+1";
で'2'と出力したのですが。
0882nobodyさん03/02/04 01:08ID:eARYiwGA
print $i+1;
0883nobodyさん03/02/04 01:10ID:???
print "${\( $i + 1 )}";
print "@{[ $i + 1 ]}";
0884nobodyさん03/02/04 01:18ID:???
>>882-883
サンクス
0885nobodyさん03/02/04 01:55ID:???
-M の返す値って実際何を表してるんですか?
出力してみても何だかわかんなくて。
0886nobodyさん03/02/04 02:04ID:CHyA5DeQ
win98にApacheとActivePerlを入れたんですがCGIファイルを実行すると
Forbiddenと出てしまいます。どこの設定がおかしいのでしょうか?
0887nobodyさん03/02/04 02:12ID:???
>>885
最後にファイルを修正してからの日数じゃないの?
てか -Mだけじゃ分からんだろ(w perl -Mの意味かと思った。

>>886
何を参考に設定したのか知らないけど、もう一度apacheの設定の仕方を見てごらん。
まぁエラーログみれば原因分かるから、それを元に検索するのも勉強。
0888nobodyさん03/02/04 03:42ID:VBD/sziN
if($a and $b){ 処理 }
は、$aと$bに何か入っていたら処理するで実際OKなのですが、
unless($a and $b){ 処理 }
ですと、両方入ってなかったら処理って風にならく、
どちらか一方でも処理に行ってしまいます。
ifのまるっきり反対じゃないんですね。何か訳があるのでしょうか?
0889nobodyさん03/02/04 03:50ID:???
>>888
小学校の「べん図」からやり直し
089088803/02/04 03:53ID:???
>>889 素早くさんきゅー 不覚だった・・・
0891nobodyさん03/02/04 04:00ID:???
ド・モルガンて名前を思い出せなくて遅れをとったYO!
089287603/02/04 09:15ID:???
すいません。。。
マルチするつもりじゃなかったんですが、書き込みした後、リロード
して確認したら書き込まれていなかったもので、スレまちがえて再書き込みして
しまいました。ご迷惑おかけしました。
いろいろなアドバイスありがとうございました。今日、がんばってみます。
0893nobodyさん03/02/04 09:28ID:???
>>888
unlessってのは、評価の結果が偽のときに実行するという命令であって、
条件式の評価の仕方が逆になるわけではない。
慣れないうちは、if (! 式) {} を使っておいたほうがいい。
0894nobodyさん03/02/04 12:16ID:ZSr84PG1
ハッシュに入れた日本語をforeachでeucにしたいのですが期待通りの結果になってくれません。
%TEST = ('A' =>'あ', 'B' => 'い');
foreach $key(keys %TEST){
&jcode'convert(*$key, "euc");
}
このやり方では駄目なのでしょうか?
0895nobodyさん03/02/04 13:08ID:???
>>894
keyをコンバートしてどないするん。
&jcode'convert(*$TEST{$key}, "euc");
やな。
0896nobodyさん03/02/04 13:19ID:???
は!
なんとマヌケな…

ありがとうございました!
以後気をつけます。
0897nobodyさん03/02/04 14:28ID:???
おう、気をつけろよ
0898 ◆hMJAPH9PWA 03/02/04 14:31ID:???
最近妙にネタが多い気がする。
089971103/02/04 14:42ID:???
オンライン翻訳についてT電子に問い合わせたら、年50万とか言われた。
なんかもう自分で作りたくなっちゃったよ。PERLでcgi形式で翻訳スクリプト
なんて作ったら、どうなるんだろ。無謀か。
0900nobodyさん03/02/04 16:42ID:???
>>899
翻訳スクリプト作れるくらいの英語力(?)があったら翻訳スクリプトなんて必要ない。
0901nobodyさん03/02/04 17:02ID:???
>>899
1.入力フォームを作る
2.入力された文章をhttp://www.infoseek.co.jp/Honyaku?pg=honyaku_t_inout.html&svx=105420&svp=SEEK
にwgetで投げる
3.getしたhtmlから結果だけを抜き出して、整形して表示
0902nobodyさん03/02/04 17:31ID:???
CGI質問スレに間違えて書き込んでしまったので、以下コピペになりますが。

ファイルを、while (<IN>) {〜}といった記述をしないで、
一行ずつ読み込んでいく方法はないものでしょうか。

@file = <IN> といったメモリにファイル全部読み込む方法は使わず、
一行ずつ読み込んで、一行ごとに違う処理をしていきたいのです。

while の中でループ回数カウントしてifで判定しろ、なんていうのはなしで。

ファイルを一行読み込む場合、
open(IN,"$logfile");
$line = <IN>;
と、やれば出きるのはどこにでも書いてあるのですが、
2度目以降 $line = <IN> としても空でした…。

Perl は一行ごとに分けるデータ構造が身についてしまってるのがダメなのかなぁ…。
seek と read 使えばよさそうなのは解ってはいるのですが、
ベースから書き換えなくてはならず、このままの構造でなんとかできないものかと。
0903nobodyさん03/02/04 17:32ID:???
>>899
変に訳されるよりはむしろ原文のままのほうがいいな…
0904nobodyさん03/02/04 17:44ID:???
infoseekのテキスト翻訳ってGETで送るのか。
変なの。
0905nobodyさん03/02/04 17:45ID:???
>>902
んなこたーない。
これを実行してみればわかる。
#!/usr/bin/perl

use strict;

our $buffer;

$buffer = <DATA>;
print $buffer;
$buffer = <DATA>;
print $buffer;
$buffer = <DATA>;
print $buffer;

__DATA__
foo
bar
baz
090690203/02/04 18:00ID:???
ほんとだ、できてますね;
どこか初歩的なミスしてそうなので探してみます。
どうもでした。
090789403/02/04 18:35ID:???
>>895さんが教えてくれた通りにやったのですがまたエラーになってしまいました。
これは他の部分がやばいのでしょうか?
0908nobodyさん03/02/04 18:49ID:???
>>907
エラーの内容を書けってば。
0909nobodyさん03/02/04 20:00ID:ifLjuw1e
gzip展開したいんですど、

open F,"/bin/gzip -d temp.txt.gz |";

できません。
どうすれば良いでしょうか。
091090903/02/04 20:12ID:???
あースマソ、できてたわ。
出力先間違ってた。
失礼しました〜
0911nobodyさん03/02/04 20:54ID:???
>>902
>ファイルを、while (<IN>) {〜}といった記述をしないで、
>一行ずつ読み込んでいく方法はないものでしょうか。

意味不明
while (<IN>) は while($_ = <IN>)と同じ
要するに一行ずつ読み込んでいる。

>Perl は一行ごとに分けるデータ構造が身についてしまってるのがダメなのかなぁ…。
身についてないと思うよ。
091271103/02/04 21:43ID:???
>>900
>翻訳スクリプト作れるくらいの英語力(?)があったら翻訳スクリプトなんて必要ない。

英語に関しては、私自身は翻訳の必要などありません。掲示板に組み込んで
多言語翻訳掲示板を作れないか、ということです。

>>901
infoseek翻訳はそういう形で利用しても大丈夫なのでしょうか?

完全にフリーのものは、殆ど日本語翻訳まではまだサポートしていないし。
http://linguaphile.sourceforge.net/
0913nobodyさん03/02/04 21:48ID:???
>>912
恐ろしく電波な掲示板になること請け合いだな。
0914nobodyさん03/02/04 22:17ID:???
>>912
infoseekはネタでしょ。では、数ヶ月ならバレナイト思われ。
091571103/02/04 22:37ID:???
捕らぬ狸のじゃないですけど、翻訳掲示板が変に繁盛し出したら
いずれはバレてしまうんでしょうね。

上のLingaphileのように、フリーの翻訳ソフトは色々
開発されてはいるようですが。
GPLTrans http://www.translator.cx/
(こっちはCとPHP?)
091689403/02/05 07:12ID:???
>>908
エラーの内容といいますと?
インターネットサーバーエラーって画面以外にもエラーってあるんですか?

一応&jcode'convert(*{$TEST{$key}}, "euc");
こんな感じにしたらエラーはでなくなりました。
しかしeucにコンバートされてないみたいです。
普通にスカラーを作って日本語を入れて検索した場合は成功しますし、
上記のハッシュに英語をいれてもちゃんとなります。

原因のわかる方がいましたらお願いします。
0917nobodyさん03/02/05 10:39ID:???
>インターネットサーバーエラーって画面以外にもエラーってあるんですか?

自分のPCにPERLをインストールして、それを使ってテストする。
そうすればもっと詳しいエラーメッセージが見れる。
0918nobodyさん03/02/05 10:44ID:???
つぅかリモートサーバでCGIのテストしてんじゃねぇよボケと。
0919nobodyさん03/02/05 11:36ID:???
>>916
Internalすら読めないのに、よくPerlのコードを書けるねえ。
意外とエラーの実体はタイプミスだったりしてな。
とりあえずレンタル鯖でのCGIテストは今すぐやめろ。
0920nobodyさん03/02/05 11:47ID:???
初心者未満のプログラマはエラーメッセージに意味があることを知らない。
よって、彼には500 Internal Server Eroorで十分だったわけだ。要はエラーが起こったという事実が大切なのだから。



実行したらエラーが出ました。助けてください。


と言う質問がいかに多いか。
0921nobodyさん03/02/05 12:38ID:???
突っ込んでいい?

Eroor
0922nobodyさん03/02/05 12:53ID:???
(゚д゚)エロォア!!
0923nobodyさん03/02/05 13:28ID:???
(゚д゚)エルゥア!!
092489403/02/05 14:37ID:???
internalでしたか。すいません。

レンタル鯖でのテストはしてませんが?
activeprelとapacheを入れてIEのアドレスにPCのアドレスを入れてやってます。
0925nobodyさん03/02/05 14:44ID:???
activeperlにapacheと入れておいて、何故エラーを500しか認識できてないのか…
百年早い。せめてperlのデバッグ方を学んで出直してこいや。
ttp://www.harukaze.net/~mishima/perl/index.html
ttp://www.harukaze.net/~mishima/perl/cgi-debug-env/deb-tech.html
この辺りな。
092689503/02/05 14:53ID:???
他の連中に怒られそうだがまぁ…
use strict;
require 'jcode.pl';

my %TEST = ('A' =>'あ', 'B' => 'い');
my $key;
foreach $key(keys %TEST){
jcode'convert(\$TEST{$key}, "euc");
}

これで動くだろ。
092789403/02/05 16:22ID:???
ありがとうございます。
895さん、925さん、その他の方にも迷惑をおかけしました。
もう少し基礎を覚え直します
0928nobodyさん03/02/05 16:52ID:???
>百年早い。
100年前にperlはない罠
0929nobodyさん03/02/05 19:58ID:???
> 100年前にperlはない罠
100年後にもPerlはない罠
0930nobodyさん03/02/05 22:39ID:???
>>926
少し直してみました。

use strict;
require 'jcode.pl';

my %TEST = ('A' => 'あ', 'B' => 'い');
foreach my $key (keys %TEST){
 jcode::convert(\$TEST{$key}, 'euc');
}

#メモリを節約:
while (my ($key, undef) = each %TEST) {
 jcode::convert(\$TEST{$key}, 'euc');
}

#他のやりかた
foreach my $value (@TEST{keys %TEST}) {
 jcode::convert(\$value, 'euc');
}
0931nobodyさん03/02/05 23:03ID:???
keyを使わないならvaluesで取り出せば良いのでは。
とか、テストコードに言うのは野暮か。
0932nobodyさん03/02/06 00:06ID:???
メモリを節約するには、どういったことに
気をつければ良いのでしょうか。
0933nobodyさん03/02/06 00:07ID:???
>>932
無駄にリストとかハッシュを多用しない。
リファレンスが使えるところはなるべくリファレンスを使う。

0934nobodyさん03/02/06 00:22ID:???
数列から先頭の文字だけ削除する
スマートな方法はないでしょうか?

$last = @DATA;
@DATA = @DATA[1..$last]
0935nobodyさん03/02/06 00:31ID:???
@DATAのリストから先頭要素を削除したいなら
shift @DATA;
093693403/02/06 00:34ID:???
>>935
ありがとうございます。(_ _ )
0937nobodyさん03/02/06 01:02ID:???
>>931
3つ目で、valuesを使わない理由は、valuesで出てきたリストに対する
変更は、%TESTに反映されないから、です。

ってそういう意味じゃないか。
0938nobodyさん03/02/06 01:03ID:???
>>934
@DATA = @DATA[1..$#DATA];
の間違いだね。
093993403/02/06 01:46ID:???
>@DATA = @DATA[1..$#DATA];

$#DATAで、配列の最後の番号ということでしょうか?
これは応用が利きそうですね。
0940nobodyさん03/02/06 03:40ID:???
.
.
.
200212.txt
200301.txt
200302.txt
こういう年月の名前のファイルを作り出すプログラムで、そのテキストの中の数字を全部足していきたいので
open(IN,"200301.txt");
open(IN,"200302.txt");
こんな感じで一個一個開いて足しているのですが、
指定した月から現在の月までのファイルを開くような方法があれば教えてください
0941nobodyさん03/02/06 05:09ID:???
>>940
readdirでファイルリストを取得して
foreach等で回しつつ、
substrや正規表現で数字を切り出して、
if($xxx >= 200212)
などという条件つけてやれば?

または、予め何月以上というリストを作ってやって、
回しつつif (-e "$_.txt")で処理するか。
0942nobodyさん03/02/06 06:20ID:???
>>940
さらにこれからはもう一つ、
年月と数値だけ羅列したインデックスファイルを作っておくと便利だと思うよ。
 ・
 ・
200302<>5648
200303<>4421
0943nobodyさん03/02/06 12:30ID:???
>>942
そういうのはインデックスとは言わない
0944nobodyさん03/02/06 15:07ID:???
>>940
そのファイル名が「4桁年2桁月」になっているのであれば、、、
$start = "200201";
$end = "200301";

foreach ($start .. $end) {
open(IN,"$_.txt");
何らかの処理
}

でよいのでは?
0945nobodyさん03/02/06 15:29ID:???
>>944
阿保ッッ!
0946nobodyさん03/02/06 17:12ID:???
200213.txtが開けません。
094794203/02/06 17:30ID:???
>>943
あい。そうでした。。。
0948nobodyさん03/02/06 19:23ID:???
時間によって何か処理をしたい場合、
例えば任意日任意時の10〜20分の間に何か処理をするとして
($minは分)
if($min >= 10 and $min <= 19){⊂}
と
if($min =~ /1[\d]/){⊂}
とやるのはどっちが高速&負荷軽めですか?
つーかもっといい方法ありますでしょうか?
0949nobodyさん03/02/06 19:49ID:???
>>948
Benchmark;
じゃダメ?
0950nobodyさん03/02/06 19:52ID:???
文字切れちゃったけど
Benchmark.pm
use Benchmarkね。
0951nobodyさん03/02/06 19:55ID:???
>>940
my ($start, $end) = (200201, 200312);

my $cnt = $start;
while($cnt <= $end){

print $cnt, ".txt\n"; # なにかしら処理

my ($year, $month) = $cnt =~ /(\d\d\d\d)(\d\d)/;

$month++;
if ($month > 12){
$month = '01';
$year++;
}

$cnt = $year. $month;
}
単純に書いてみました。
0952別スレの優雅な94803/02/06 20:02ID:???
>>948
処理の重さだけなら後者が約2.2倍重いです。
前者を200万回処理するのにかかった時間0.69秒
後者を200万回処理するのにかかった時間1.51秒
実験は当方ローカル環境(CPU2.5GHz)

定期的に処理をしたいのであれば、UNIXコマンドのcronがありますが、
借りているサーバがshellを許可しているか、コントロールパネルにより
提供している必要がります。
0953郵政の歴史年表 03/02/06 21:24ID:iDPmTn07
perlを使って、
http://www.iptp.go.jp/museum/yusei/tsushin/nenpyou.html
にある1860年代から1990年代までの中から、
「郵便貯金の歴史」だけをgrep見たいに抜き出すこと出来ますか?

0954nobodyさん03/02/06 21:29ID:???
>>953
できるよ。

まず、そのサイトのデータを全部ダウンロードしてローカルに置きましょう。
(以下略)
0955nobodyさん03/02/06 21:30ID:???
ローカルに置いてからperlを使ってsystem("/bin/grep")てな感じ。














そうじゃないだろ・・・・
0956(=`ェ´=) ◆9rperl5mn2 03/02/06 21:31ID:???
>>953 作ればできるよん。
0957nobodyさん03/02/06 21:47ID:???
<tr>
<td valign=top nowrap><b>([^<]*)</b></td>
<td>

<tr>
<td valign=top><font color=(?:ff9cff|9cff31|0031ff)>●</font></td>
<td>([^<]*)</td>
</tr>
0958nobodyさん03/02/06 21:53ID:???
>>948
はっきりいってそんなのperlの起動コストやI/Oコストに比べればゴミみたいなもん
分かりやすい方選んどき
0959nobodyさん03/02/07 03:13ID:Md2X1ufV
POSTで受け取ったファイルの、
アップロードする前のオリジナルネームは
どこを参照すればわかるのでしょうか?
 環境変数 Perl 一覧
などとググっても見つけられませんでした。
よろしくご教示ください。
0960nobodyさん03/02/07 03:32ID:???
multipartでPOSTした場合はContent-dispositionヘッダ。
http://www.yo.rim.or.jp/~getsu/document/rfc1867j.txt

こういう意味じゃない?
0961nobodyさん03/02/07 03:55ID:???
>>960
なるほど。格納されている場所がわかりました。
実際の取得方法(スカラー変数への代入)を調べてみます。
ありがとうございました。
0962nobodyさん03/02/07 16:46ID:04vl2wLA
指定したディレクトリにあるファイルのファイル名を
全て配列に代入するにはどうすればいいんでしょうか?

例えば、cgi本体と同じ階層にある「log」というディレクトリに
0.dat,1.dat,2.datがある時に、
最終的に@dataに0.dat,1.dat,2.datが代入されている
という風にするにはどうするのでしょうか?
0963nobodyさん03/02/07 16:54ID:???
opendir
0964nobodyさん03/02/07 16:54ID:???
>>962
http://homepage2.nifty.com/sak/w_sak3/doc/sysbrd/pe_k03.htm
0965名無しさん@Meadow03/02/07 17:01ID:???
>>962
サブディレクトリもでしょ。.とか..とかのディレクトリは
入れないんでしょ。これでいいと思うよ。

#!/usr/local/bin/perl

# コマンドラインで指定したディレクトリの中にあるすべてのファイルを配列に入れる
$usage = 'perl files-in-dir.pl 絶対パス';
$starting_dir = shift;
die $usage if $starting_dir eq "";

sub search {
my($dir, $depth) = @_;
my $handle = "DIR$depth";
opendir($handle, $dir) or die $!;
while($file = readdir($handle)) {
next if $file =~ /^\.{1,2}$/;
if (-d "$dir/$file") {
&search("$dir/$file", $depth + 1);
} else {
push(@files, $file);
}
}
closedir($handle);
}

search("$starting_dir", 1);

for(@files) {
print;
}
096696203/02/07 17:40ID:???
解決しました。皆さんありがとうございました。
0967nobodyさん03/02/07 21:04ID:???
モジュール使えよ
0968nobodyさん03/02/07 21:06ID:???
>>967
はいはい。
0969nobodyさん03/02/08 00:03ID:???
Perl初心者さんへ、世の中PHPに移行する中、
なんでPerlを覚えてるの?
借りてるサーバがPerlしか使えないとかかな?
マジレスきぼん。
0970マジレス03/02/08 00:06ID:???
どんな世の中だっつの。おまえの頭の中のか?
0971nobodyさん03/02/08 00:23ID:???
>>970
初心者さん マジレスありがとう。  
0972nobodyさん03/02/08 00:24ID:???
>969
( ´,_ゝ`) プッ
0973しょしんしゃ03/02/08 00:26ID:qxZih98+
ファイル処理プロセスが面倒
日本語処理が面倒
ソケット通信が未熟
0974nobodyさん03/02/08 00:43ID:???
社員番号 社員名 身長   体重
$no     $name $heught $weight

とする場合、身長の降順、同じ場合は体重の昇順に
体重まで同じ場合は、さらに社員番号の昇順に
社員番号、社員名、身長、体重をprintしたい場合は
どうしたらよいでしょうか?(複数キー)
097594003/02/08 01:27ID:???
ありがとうございました
0976nobodyさん03/02/08 02:04ID:???
>>974
まずは色々とやってみる。
それでだめならぐぐる。

それくらいのことをしないと初心者とは認定されませぬぞ。
レス数が950を超えています。1000を超えると書き込みができなくなります。