IO#gets は、コマンド ラインから入力をキャプチャする場合と同じように機能します。「Enter」は入力の一部として送信されません。ファイルまたは IO の他のサブクラスで #gets が呼び出されたときにも渡されないため、数値は確実に一致しません。
関連するつるはしセクションを参照してください
行の長さの合計がファイル サイズになることをなぜそんなに気にかけているのかお尋ねしてもよろしいですか? 必要以上に難しい問題を解いているかもしれません...
あはは。私は今それを得ると思います。
便利な iPod (またはその他の種類) がないので、正確に 4K のチャンクが必要かどうかはわかりません。行ごとに分割する方が幸せです。その場合、次のようなものが機能するはずです。
class Chunkifier
def Chunkifier.to_chunks(path)
chunks, current_chunk_size = [""], 0
File.readlines(path).each do |line|
line.chomp! # strips off \n, \r or \r\n depending on OS
if chunks.last.size + line.size >= 4_000 # 4096?
chunks.last.chomp! # remove last line terminator
chunks << ""
end
chunks.last << line + "\n" # or whatever terminator you need
end
chunks
end
end
if __FILE__ == $0
require 'test/unit'
class TestFile < Test::Unit::TestCase
def test_chunking
chs = Chunkifier.to_chunks(PATH)
chs.each do |chunk|
assert 4_000 >= chunk.size, "chunk is #{chunk.size} bytes long"
end
end
end
end
すべてのテキストを 1 回のスラープで取得するために IO#readlines を使用していることに注意してください: #each または #each_line も同様です。String#chomp を使用しました。OSが何をしていても、最後のバイトが削除されるようにするため、 \n または何でも出力に強制できるようになります。
出力には #print や #puts ではなく File#write を使用することをお勧めします。後者は OS 固有の改行シーケンスを提供する傾向があるためです。
マルチバイト文字が本当に気になる場合は、each_byte または unpack(C*) オプションを使用して、次のようなモンキー パッチ文字列を使用することを検討してください。
class String
def size_in_bytes
self.unpack("C*").size
end
end
unpack バージョンは、私のマシンの each_byte バージョンよりも約 8 倍高速です。