質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

90.83%

  • Perl

    435questions

    Perlは多目的に使用される実用性が高い動的プログラミング言語のひとつです。

Perlの文書読み込み及びその内容の編集に関する質問です

解決済

回答 3

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 95

perlstarter

score 1

 前提

(助言を受け編集しました)
perlの超初心者です。初歩的な質問ですみません。読み込んだ文書をsortして、新しい文書に書き込みたいです。
具体的に:
"I am a student. I go to school."を
"a am go I I school. student. to" みたいな感じにしたいです。
しかし、現在は
"a am I student. go I school to." みたいになってます。どうすれば段落ごとではなく全文書を並べ替えられますか?

自分がやってみたのは以下の通りです。

 発生している問題・エラーメッセージ

open(TEXT, "< 元の文書");

$new = "保存する場所";
open(NEW, "> $new");

foreach $line(<TEXT>){
   @line = split(/ /,$line);
   @line = sort(@line);
   print NEW "@line";
}

close (TEXT);
close (NEW);

 該当のソースコード

perl

 エラー

保存する場所では段落ごと?行ごと?に並べ替えられています。

 補足情報(FW/ツールのバージョンなど)

ここにより詳細な情報を記載してください。

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

質問への追記・修正、ベストアンサー選択の依頼

  • perlstarter

    2018/06/25 00:29

    えと、これで合ってますか(汗) 教科書は持っていないので、先生のPPTを見て他のページで調べました(汗)

    キャンセル

  • KojiDoi

    2018/06/25 02:38

    はい、そんな感じでOKです。うるさいこと言いやがってと思ったかもしれませんが、少し長いスクリプトを書き始めると、インデントがいい加減だと絶対にドツボにハマります。今のうちにきれいなコードを書く習慣をつけてください。

    キャンセル

  • perlstarter

    2018/06/25 15:47

    いえいえ、わざわざ教えて頂きありがとうございます!

    キャンセル

回答 3

checkベストアンサー

+1

× $new = "> 新しいファイル名と場所.txt";
○ $new = "新しいファイル名と場所.txt";

並べ替えられるのは全文書ではなく段落ごと。

最初のループで、一行読んでは@lineを設定し直しているので、最後の段落しか残りませんね。

追記 

要件修正を踏まえて、”丸呑み”処理を加えます。 修正個所のみ示します。テストしていませんが多分うまく行く筈。 

...
foreach $line (<TEXT>){
   push(@line, split(/ /,$line));
}

print NEW join(" ", sort @line), "\n";

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2018/06/24 23:46

    回答ありがとうございます。最初のループはどういう風に書けば良いのでしょうか...授業での説明ではあまり読み込みについて説明がなかったのでこれ全部でテキストの読み込みだと思っていました...
    本当に初歩的な質問ですみません。

    キャンセル

  • 2018/06/25 00:12

    まずループを二つ作る必要がないですね。最初のループの中で、読んだらすぐにソートして出力するようにすればいいのです。

    キャンセル

  • 2018/06/25 15:51

    ありがとうございます。いらない部分をを消して、書き換えてみました。エラーも出なくなり、文書が新しいファイルに書き込まれるようになったのですが、やはり段落ごとに並べ替えられています。段落ごとではなく全文書を通してならべかえるにはどうすべきでしょうか...?

    キャンセル

  • 2018/06/25 16:04

    要件を読み間違えていたようなので前のコメントは取り消します。
    全文書通しての処理となれば、読込み専用のループを作ってデータを丸呑みする必要があります。

    キャンセル

  • 2018/06/25 21:33

    うまくいきました!本当にありがとうございます!初心者レベルの質問から基礎まで本当に勉強になりました!ありがとうございました!

    キャンセル

0

$new = "> 新しいファイル名と場所.txt";
open(NEW, "> $new");

この時点で、openの引数で>が重複していて、ファイルハンドルNEWが想定通りの出力先になっていないと思います。

なお、そもそもの問題として2引数のopenは色々問題が起り易いので、今時はお勧めしません。3変数、かつ生のファイルハンドルを避けて、

open my $ifh, '<', 'inputfilename'; # 読み込み用にopen
foreach my $line ( <$ifh> ) {
…
}
open my $ofh, '>', 'outputfilename'; # 書き込み用にopenprint $ofh "$word\n";

のような使い方が良いです。( 或いはIO::Fileモジュールを使う方法もあります )

その問題とは別に、ファイルに出力する元となる@lineは、最初のループの最後の実行時に保存された内容、すなわち読み込んだファイルの最終行を分割・ソートした内容になっているのですが、それは意図通りなのでしょうか?

テキストの読み込み → 文章を単語ごとにsplit → アルファベット順に並べ替え → 新しいファイルに書き込む ということしたい

手順よりも先に、望む結果を明らかにした方が良いと思います。結果に至る手順は1通りではないですし、考えた結果が適切とも限りませんから。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2018/06/24 23:57

    回答ありがとうございます!
    ファイルの>については解決しました!
    @lineの部分ですが、意図したことは特にありません(泣)
    望む結果は、読み込んだ文書を単語単位でアルファベット順にして新しいファイルに書き込むことです。
    始めたばかりで初歩的な質問や問題ばかりですみません...

    キャンセル

  • 2018/06/25 00:06

    もうちょっと曖昧さをなくすように整理した方が良いかな、と。
    入力ファイルを何かしら加工して新しいファイル書き込む、アルファベット順にするにしても、例えば、入力ファイルの各行と新しいファイルの各行は対応するんですか、とか。
    アルファベット順にするのは全ファイルを通じてなのか、行の中だけなんですか、とか。

    サンプルを1つ例示して貰った方が、多分スムーズに行きます。例えば、

    ```
    a c b
    e d f
    ```

    という2行のファイルを入力とした場合、望む出力ファイルはどんなふうになっているんですか、と。

    ```
    a b c
    d e f
    ```

    なのか

    ```
    a
    b

    ```

    なのか、とか。

    キャンセル

  • 2018/06/25 00:22

    全ファイルを通して...です!ありがとうございます。具体例を入れました!

    キャンセル

0

Perlなど不要。そう、シェル芸ならね!

$ cat 場所とテキスト.txt|while read l;do echo $l|tr ' ' '\n'|sort|xargs;done > 新しいファイル名と場所.txt

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2018/06/24 23:59

    いや、それなら次のperlワンライナーでしょう…
    $ perl -ple '$_=join" ",sort split' 場所とテキスト.txt > 新しいファイル名と場所.txt
    こっちでも良いかも
    $ perl -plae '$_=join" ",sort@F' 場所とテキスト.txt > 新しいファイル名と場所.txt

    キャンセル

  • 2018/06/25 02:46 編集

    個人的にはこの案件でシェルスクリプトはないなあ。最初はシェルで行けるかとやってみるが、やはりややこしくなってperlでやり直すパターンですね、私の場合は。

    ちなみに、windows10上のcygwinのtimeコマンドで両方を測定してみたところ次の結果を得ました。
    これはたまたま手元にあった10桁x100行のファイルを対象とした結果です。
    シェル芸:
    real 0m15.232s
    user 0m1.957s
    sys 0m13.724s
    perl ワンライナー:
    real 0m0.075s
    user 0m0.031s
    sys 0m0.015s

    ついでに250桁x100行のファイルではこうなりました。
    シェル芸:
    real 0m15.154s
    user 0m2.309s
    sys 0m13.641s
    perl ワンライナー:
    real 0m0.106s
    user 0m0.015s
    sys 0m0.030s

    キャンセル

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 90.83%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

関連した質問

  • 解決済

    perl でキーワードからキーワードの間の行を抽出したい

    perl本当の初心者です。とても苦戦しています。 地名1.csv 地名2.csv の2つのファイルがあったとします。 ==地名1.csv== a,b,札幌,c,d,

  • 解決済

    perl初心者:perlでコマンド結果に応じて

    すみません、初歩的な質問で恐縮です。 perlで外部コマンドの結果に応じて処理をするscriptを作りたいのですが、 教えて頂けないでしょうか。 例:外部コマンドをper

  • 受付中

    perlでsedの置換ができない

    perlでsedの置換ができなくて困っています。 $sr1="123"; $sr2="456"; $answer = sed -i -e s/$sr1/$sr2/ /

  • 解決済

    perlによる文字変換スクリプト

    漢字かな混じりの文章ファイルと、単語とその読みを記載したファイルの2つを用いて文章を全てひらがなに変換するスクリプトを作成したいと考えているのですが、上手くいく方法が思い浮かばず困

  • 解決済

    1行ごとに入力されている各単語の数を数えたい

    閲覧ありがとうございます。 一単語が一行に入力されたtxtファイルの中の 各単語が何回出てきているかを調べたいのですが、どのようにすればよいでしょうか? 単語を指定し

  • 解決済

    perl正規表現,置換ができません

    前提・実現したいこと テキストファイルA.txt中にある文字 「A」を「B」に置換し, 別のテキストファイルBへ出力したいのですが, エラーが出てしまいます。 発生している問題

  • 解決済

    perl 検索範囲指定

    前提実現したいこと perlでhoge.txtのデータの一部を置換してhogehoge.txtにコピーしたいと考えています。 hoge.txtの中身 <ccc> abcde

  • 解決済

    perlで特定の文字列が出現するごとにその区間を分割してファイルに保存する方法

    いつもお世話になっております。 文字列の羅列された1つのファイルに対して、特定の文字列同士の間の区間ごとにファイルを分割して保存するスクリプトを書こうとしています。 例えば、 XX

同じタグがついた質問を見る

  • Perl

    435questions

    Perlは多目的に使用される実用性が高い動的プログラミング言語のひとつです。