Ekstrak teks di antara tiga kutipan tunggal

8

Saya memiliki yang berikut dalam sebuah file

description: '''
        This rule forbids throwing string literals or interpolations. While
        JavaScript (and CoffeeScript by extension) allow any expression to
        be thrown, it is best to only throw <a
        href="https://developer.mozilla.org
        /en/JavaScript/Reference/Global_Objects/Error"> Error</a> objects,
        because they contain valuable debugging information like the stack
        trace. Because of JavaScript's dynamic nature, CoffeeLint cannot
        ensure you are always throwing instances of <tt>Error</tt>. It will
        only catch the simple but real case of throwing literal strings.
        <pre>
        <code># CoffeeLint will catch this:
        throw "i made a boo boo"

        # ... but not this:
        throw getSomeString()
        </code>
        </pre>
        This rule is enabled by default.
        '''

dengan beberapa hal lain dalam file ini.

Saya mengekstrak bagian ini dalam skrip shell saya melalui sed -n "/'''/,/'''/p" $1(di mana $1file).

Ini memberi saya variabel dengan konten sebagai satu liner

description: ''' This rule forbids throwing string literals or interpolations. While JavaScript (and CoffeeScript by extension) allow any expression to be thrown, it is best to only throw <a href="https://developer.mozilla.org /en/JavaScript/Reference/Global_Objects/Error"> Error</a> objects, because they contain valuable debugging information like the stack trace. Because of JavaScript's dynamic nature, CoffeeLint cannot ensure you are always throwing instances of <tt>Error</tt>. It will only catch the simple but real case of throwing literal strings. <pre> <code># CoffeeLint will catch this: throw "i made a boo boo" # ... but not this: throw getSomeString() </code> </pre> This rule is enabled by default. '''

Bagaimana saya sekarang dapat mengekstrak bagian antara '''?

Atau bahkan ada cara yang lebih baik untuk mengambilnya dari file multiline?

Saya menggunakan Mac El Captain 10.11.2 dan GNU bash, versi 3.2.57 (1) -release (x86_64-apple-darwin15)

Cod Emerson
sumber
3
Letakkan tanda kutip ganda di sekitar variabel, itu berisi baris baru.
DisplayName
1
Ini YAML, kan? Apa alasan Anda sebenarnya tidak menggunakan parser YAML?
Charles Duffy
@DisplayName, ... agar jelas, maksud Anda tanda kutip ganda saat bergema , kan?
Charles Duffy

Jawaban:

12
perl -l -0777 -ne "print for /'''(.*?)'''/gs" file

akan mengekstrak (dan mencetak diikuti oleh baris baru) bagian antara setiap pasangan '' '.

Berhati-hatilah karena perlmenghirup seluruh file dalam memori sebelum mulai memprosesnya sehingga solusi mungkin tidak sesuai untuk file yang sangat besar.

Stéphane Chazelas
sumber
7

Coba ini, jika Anda memiliki gawkatau mawkuntuk pembuangan Anda:

gawk -v "RS='''" 'FNR%2==0' file

Ini mengasumsikan bahwa tidak ada yang lain '''di file.

Penjelasan: Ini mengatur pemisah rekaman ke tiga tanda kutip tunggal, dan mencetak jika nomor catatan genap.

Sayangnya, itu tidak akan berfungsi dengan semua awkimplementasi, karena Pemisah Catatan multi-karakter bukan bagian dari POSIX awk.

joepd
sumber
Terminal (saya) Mac tidak tahu gawk per default.
Emerson Cod
4

Tidak sebagus jawaban awk tetapi karena Anda awalnya menggunakan sed

/'''/{
   s/.*'''//
   :1
   N
   /'''/!b1
   s/'''.*//
   p
}
d

Atau lebih pendek seperti yang ditunjukkan oleh glenn jackman di komentar (sedikit berubah)

/'''/,//{
//!p
}
d

Jalankan sebagai

sed -f script file

Keluaran

    This rule forbids throwing string literals or interpolations. While
    JavaScript (and CoffeeScript by extension) allow any expression to
    be thrown, it is best to only throw <a
    href="https://developer.mozilla.org
    /en/JavaScript/Reference/Global_Objects/Error"> Error</a> objects,
    because they contain valuable debugging information like the stack
    trace. Because of JavaScript's dynamic nature, CoffeeLint cannot
    ensure you are always throwing instances of <tt>Error</tt>. It will
    only catch the simple but real case of throwing literal strings.
    <pre>
    <code># CoffeeLint will catch this:
    throw "i made a boo boo"

    # ... but not this:
    throw getSomeString()
    </code>
    </pre>
    This rule is enabled by default.
123
sumber
1
Anda dapat menyingkat sed itu sed -n "/'''/,//{//!p}"- mungkin harus dilakukan set +Hterlebih dahulu di bash untuk mematikan ekspansi sejarah.
glenn jackman
@glennjackman Itulah alasan saya memasukkannya ke dalam skrip, IMO selalu lebih mudah dibaca dan kebal terhadap fungsi shell seperti globbing, ekspansi dll. Pokoknya saya menambahkannya ke jawaban saya karena lebih ringkas daripada skrip asli saya.
123