mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
parent
21fa0135a4
commit
841be6392e
Notes:
git
2022-10-24 15:38:39 +00:00
Merged-By: BurdetteLamar <BurdetteLamar@Yahoo.com>
1 changed files with 188 additions and 260 deletions
|
@ -87,31 +87,28 @@ Many examples here use these variables:
|
|||
|
||||
=== Basic \IO
|
||||
|
||||
==== Reading and Writing
|
||||
You can perform basic stream \IO with these methods:
|
||||
|
||||
===== \Method <tt>#read</tt>
|
||||
- IO#read: Returns all remaining or the next _n_ bytes read from the stream,
|
||||
for a given _n_:
|
||||
|
||||
Returns all remaining or the next +n+ bytes read from the stream, for a given +n+:
|
||||
f = File.new('t.txt')
|
||||
f.read # => "First line\nSecond line\n\nFourth line\nFifth line\n"
|
||||
f.rewind
|
||||
f.read(30) # => "First line\r\nSecond line\r\n\r\nFou"
|
||||
f.read(30) # => "rth line\r\nFifth line\r\n"
|
||||
f.read(30) # => nil
|
||||
f.close
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.read # => "First line\nSecond line\n\nFourth line\nFifth line\n"
|
||||
f.rewind
|
||||
f.read(30) # => "First line\r\nSecond line\r\n\r\nFou"
|
||||
f.read(30) # => "rth line\r\nFifth line\r\n"
|
||||
f.read(30) # => nil
|
||||
f.close
|
||||
- IO#write: Writes one or more given strings to the stream:
|
||||
|
||||
===== \Method <tt>#write</tt>
|
||||
$stdout.write('Hello', ', ', 'World!', "\n") # => 14
|
||||
$stdout.write('foo', :bar, 2, "\n")
|
||||
|
||||
Writes one or more given strings to the stream:
|
||||
Output:
|
||||
|
||||
$stdout.write('Hello', ', ', 'World!', "\n") # => 14
|
||||
$stdout.write('foo', :bar, 2, "\n")
|
||||
|
||||
Output:
|
||||
|
||||
Hello, World!
|
||||
foobar2
|
||||
Hello, World!
|
||||
foobar2
|
||||
|
||||
==== Position
|
||||
|
||||
|
@ -120,112 +117,92 @@ which is the byte offset at which the next read or write is to occur.
|
|||
A new stream has position zero (and line number zero);
|
||||
method +rewind+ resets the position (and line number) to zero.
|
||||
|
||||
===== \Method <tt>#tell</tt>
|
||||
The relevant methods:
|
||||
|
||||
Returns the current position (in bytes) in the stream:
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.tell # => 0
|
||||
f.gets # => "First line\n"
|
||||
f.tell # => 12
|
||||
f.close
|
||||
|
||||
Aliased as <tt>pos</tt>.
|
||||
|
||||
===== \Method <tt>#pos=</tt>
|
||||
|
||||
Sets the position of the stream (in bytes):
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.tell # => 0
|
||||
f.pos = 20 # => 20
|
||||
f.tell # => 20
|
||||
f.close
|
||||
|
||||
===== \Method <tt>#seek</tt>
|
||||
|
||||
Sets the position of the stream to a given integer +offset+
|
||||
(in bytes), with respect to a given constant +whence+, which is one of:
|
||||
|
||||
- +:CUR+ or <tt>IO::SEEK_CUR</tt>:
|
||||
Repositions the stream to its current position plus the given +offset+:
|
||||
- IO#tell (aliased as +#pos+):
|
||||
Returns the current position (in bytes) in the stream:
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.tell # => 0
|
||||
f.seek(20, :CUR) # => 0
|
||||
f.tell # => 20
|
||||
f.seek(-10, :CUR) # => 0
|
||||
f.tell # => 10
|
||||
f.tell # => 0
|
||||
f.gets # => "First line\n"
|
||||
f.tell # => 12
|
||||
f.close
|
||||
|
||||
- +:END+ or <tt>IO::SEEK_END</tt>:
|
||||
Repositions the stream to its end plus the given +offset+:
|
||||
- IO#pos=: Sets the position of the stream (in bytes):
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.tell # => 0
|
||||
f.seek(0, :END) # => 0 # Repositions to stream end.
|
||||
f.tell # => 52
|
||||
f.seek(-20, :END) # => 0
|
||||
f.tell # => 32
|
||||
f.seek(-40, :END) # => 0
|
||||
f.tell # => 12
|
||||
f.tell # => 0
|
||||
f.pos = 20 # => 20
|
||||
f.tell # => 20
|
||||
f.close
|
||||
|
||||
- +:SET+ or <tt>IO:SEEK_SET</tt>:
|
||||
Repositions the stream to the given +offset+:
|
||||
- IO#seek: Sets the position of the stream to a given integer +offset+
|
||||
(in bytes), with respect to a given constant +whence+, which is one of:
|
||||
|
||||
- +:CUR+ or <tt>IO::SEEK_CUR</tt>:
|
||||
Repositions the stream to its current position plus the given +offset+:
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.tell # => 0
|
||||
f.seek(20, :CUR) # => 0
|
||||
f.tell # => 20
|
||||
f.seek(-10, :CUR) # => 0
|
||||
f.tell # => 10
|
||||
f.close
|
||||
|
||||
- +:END+ or <tt>IO::SEEK_END</tt>:
|
||||
Repositions the stream to its end plus the given +offset+:
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.tell # => 0
|
||||
f.seek(0, :END) # => 0 # Repositions to stream end.
|
||||
f.tell # => 52
|
||||
f.seek(-20, :END) # => 0
|
||||
f.tell # => 32
|
||||
f.seek(-40, :END) # => 0
|
||||
f.tell # => 12
|
||||
f.close
|
||||
|
||||
- +:SET+ or <tt>IO:SEEK_SET</tt>:
|
||||
Repositions the stream to the given +offset+:
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.tell # => 0
|
||||
f.seek(20, :SET) # => 0
|
||||
f.tell # => 20
|
||||
f.seek(40, :SET) # => 0
|
||||
f.tell # => 40
|
||||
f.close
|
||||
|
||||
- IO#rewind: Positions the stream to the beginning (also resetting the line number):
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.tell # => 0
|
||||
f.seek(20, :SET) # => 0
|
||||
f.tell # => 20
|
||||
f.seek(40, :SET) # => 0
|
||||
f.tell # => 40
|
||||
f.tell # => 0
|
||||
f.gets # => "First line\n"
|
||||
f.tell # => 12
|
||||
f.rewind # => 0
|
||||
f.tell # => 0
|
||||
f.lineno # => 0
|
||||
f.close
|
||||
|
||||
===== \Method <tt>#rewind</tt>
|
||||
|
||||
Positions the stream to the beginning (also resetting the line number):
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.tell # => 0
|
||||
f.gets # => "First line\n"
|
||||
f.tell # => 12
|
||||
f.rewind # => 0
|
||||
f.tell # => 0
|
||||
f.lineno # => 0
|
||||
f.close
|
||||
|
||||
==== Open and Closed Streams
|
||||
|
||||
A new \IO stream may be open for reading, open for writing, or both.
|
||||
|
||||
===== \Method <tt>#close</tt>
|
||||
You can close a stream using these methods:
|
||||
|
||||
Closes the stream for both reading and writing.
|
||||
- IO#close: Closes the stream for both reading and writing.
|
||||
- IO#close_read (not in \ARGF): Closes the stream for reading.
|
||||
- IO#close_write (not in \ARGF): Closes the stream for writing.
|
||||
|
||||
===== \Method <tt>#close_read</tt>
|
||||
You can query whether a stream is closed using this method:
|
||||
|
||||
Closes the stream for reading,
|
||||
|
||||
Not in ARGF.
|
||||
|
||||
===== \Method <tt>#close_write</tt>
|
||||
|
||||
Closes the stream for writing
|
||||
|
||||
Not in ARGF.
|
||||
|
||||
===== \Method <tt>#closed?</tt>
|
||||
|
||||
Returns whether the stream is closed.
|
||||
- IO#closed?: Returns whether the stream is closed.
|
||||
|
||||
==== End-of-Stream
|
||||
|
||||
===== \Method <tt>#eof?</tt>
|
||||
|
||||
Returns whether a stream is positioned at its end; aliased as +#eof+.
|
||||
|
||||
===== Repositioning to End-of-Stream
|
||||
You can query whether a stream is positioned at its end using
|
||||
method IO#eof? (also aliased as +#eof+).
|
||||
|
||||
You can reposition to end-of-stream by reading all stream content:
|
||||
|
||||
|
@ -243,65 +220,52 @@ Or by using method IO#seek:
|
|||
|
||||
=== Line \IO
|
||||
|
||||
You can process an \IO stream line-by-line.
|
||||
You can read an \IO stream line-by-line using these methods:
|
||||
|
||||
===== \Method <tt>#each_line</tt>
|
||||
- IO#each_line: Passes each line to the block:
|
||||
|
||||
Passes each line to the block:
|
||||
f = File.new('t.txt')
|
||||
f.each_line {|line| p line }
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.each_line {|line| p line }
|
||||
Output:
|
||||
|
||||
Output:
|
||||
"First line\n"
|
||||
"Second line\n"
|
||||
"\n"
|
||||
"Fourth line\n"
|
||||
"Fifth line\n"
|
||||
|
||||
"First line\n"
|
||||
"Second line\n"
|
||||
"\n"
|
||||
"Fourth line\n"
|
||||
"Fifth line\n"
|
||||
The reading may begin mid-line:
|
||||
|
||||
The reading may begin mid-line:
|
||||
f = File.new('t.txt')
|
||||
f.pos = 27
|
||||
f.each_line {|line| p line }
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.pos = 27
|
||||
f.each_line {|line| p line }
|
||||
Output:
|
||||
|
||||
Output:
|
||||
"rth line\n"
|
||||
"Fifth line\n"
|
||||
|
||||
"rth line\n"
|
||||
"Fifth line\n"
|
||||
- IO#gets (also in Kernel): Returns the next line (which may begin mid-line):
|
||||
|
||||
===== \Method <tt>#gets</tt>
|
||||
f = File.new('t.txt')
|
||||
f.gets # => "First line\n"
|
||||
f.gets # => "Second line\n"
|
||||
f.pos = 27
|
||||
f.gets # => "rth line\n"
|
||||
f.readlines # => ["Fifth line\n"]
|
||||
f.gets # => nil
|
||||
|
||||
Returns the next line (which may begin mid-line); also in Kernel:
|
||||
- IO#readline (also in Kernel; not in StringIO):
|
||||
Like #gets, but raises an exception at end-of-stream.
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.gets # => "First line\n"
|
||||
f.gets # => "Second line\n"
|
||||
f.pos = 27
|
||||
f.gets # => "rth line\n"
|
||||
f.readlines # => ["Fifth line\n"]
|
||||
f.gets # => nil
|
||||
- IO#readlines (also in Kernel): Returns all remaining lines in an array;
|
||||
may begin mid-line:
|
||||
|
||||
===== \Method <tt>#readline</tt>
|
||||
|
||||
Like #gets, but raises an exception at end-of-stream.
|
||||
|
||||
Also in Kernel; not in StringIO.
|
||||
|
||||
===== \Method <tt>#readlines</tt>
|
||||
|
||||
Returns all remaining lines in an array;
|
||||
may begin mid-line:
|
||||
|
||||
f = File.new('t.txt')
|
||||
f.pos = 19
|
||||
f.readlines # => ["ine\n", "\n", "Fourth line\n", "Fifth line\n"]
|
||||
f.readlines # => []
|
||||
|
||||
Also in Kernel.
|
||||
|
||||
===== Optional Reader Arguments
|
||||
f = File.new('t.txt')
|
||||
f.pos = 19
|
||||
f.readlines # => ["ine\n", "\n", "Fourth line\n", "Fifth line\n"]
|
||||
f.readlines # => []
|
||||
|
||||
Each of these reader methods may be called with:
|
||||
|
||||
|
@ -309,16 +273,14 @@ Each of these reader methods may be called with:
|
|||
- An optional line-size limit, +limit+.
|
||||
- Both +sep+ and +limit+.
|
||||
|
||||
===== \Method <tt>#puts</tt>
|
||||
You can write to an \IO stream line-by-line using this method:
|
||||
|
||||
Writes objects to the stream:
|
||||
- IO#puts (also in Kernel; not in \StringIO): Writes objects to the stream:
|
||||
|
||||
f = File.new('t.tmp', 'w')
|
||||
f.puts('foo', :bar, 1, 2.0, Complex(3, 0))
|
||||
f.flush
|
||||
File.read('t.tmp') # => "foo\nbar\n1\n2.0\n3+0i\n"
|
||||
|
||||
Also in Kernel; not in StringIO.
|
||||
f = File.new('t.tmp', 'w')
|
||||
f.puts('foo', :bar, 1, 2.0, Complex(3, 0))
|
||||
f.flush
|
||||
File.read('t.tmp') # => "foo\nbar\n1\n2.0\n3+0i\n"
|
||||
|
||||
==== Line Separator
|
||||
|
||||
|
@ -406,21 +368,13 @@ which is the non-negative integer line number
|
|||
in the stream where the next read will occur.
|
||||
|
||||
The line number is the number of lines read by certain line-oriented methods
|
||||
({::foreach}[rdoc-ref:IO.foreach],
|
||||
{#each_line}[rdoc-ref:io_streams.rdoc@Method+-23each_line],
|
||||
{#gets}[rdoc-ref:io_streams.rdoc@Method+-23gets],
|
||||
{#readline}[rdoc-ref:io_streams.rdoc@Method+-23readline],
|
||||
{#readlines}[rdoc-ref:io_streams.rdoc@Method+-23readlines])
|
||||
(IO.foreach, IO#each_line, IO#gets, IO#readline, and IO#readlines)
|
||||
according to the given (or default) line separator +sep+.
|
||||
|
||||
A new stream is initially has line number zero (and position zero);
|
||||
method +rewind+ resets the line number (and position) to zero.
|
||||
|
||||
===== \Method <tt>#lineno</tt>
|
||||
|
||||
Returns the line number.
|
||||
|
||||
===== Changes to the Line Number
|
||||
\Method IO#lineno returns the line number.
|
||||
|
||||
Reading lines from a stream usually changes its line number:
|
||||
|
||||
|
@ -460,128 +414,102 @@ that determine how lines in a stream are to be treated:
|
|||
|
||||
=== Character \IO
|
||||
|
||||
You can process an \IO stream character-by-character.
|
||||
You can process an \IO stream character-by-character using these methods:
|
||||
|
||||
===== \Method <tt>#getc</tt>
|
||||
- IO#getc: Reads and returns the next character from the stream:
|
||||
|
||||
Reads and returns the next character from the stream:
|
||||
f = File.new('t.rus')
|
||||
f.getc # => "т"
|
||||
f.getc # => "е"
|
||||
f.getc # => "с"
|
||||
f.getc # => "т"
|
||||
f.getc # => nil
|
||||
|
||||
f = File.new('t.rus')
|
||||
f.getc # => "т"
|
||||
f.getc # => "е"
|
||||
f.getc # => "с"
|
||||
f.getc # => "т"
|
||||
f.getc # => nil
|
||||
- IO#readchar (not in \StringIO):
|
||||
Like #getc, but raises an exception at end-of-stream:
|
||||
|
||||
===== \Method <tt>#readchar</tt>
|
||||
f.readchar # Raises EOFError.
|
||||
|
||||
Like #getc, but raises an exception at end-of-stream.
|
||||
- IO#ungetc (not in \ARGF):
|
||||
Pushes back ("unshifts") a character or integer onto the stream:
|
||||
|
||||
Not in \StringIO.
|
||||
path = 't.tmp'
|
||||
File.write(path, 'foo')
|
||||
File.open(path) do |f|
|
||||
f.ungetc('т')
|
||||
f.read # => "тfoo"
|
||||
end
|
||||
|
||||
===== \Method <tt>#ungetc</tt>
|
||||
- IO#putc (also in Kernel): Writes a character to the stream:
|
||||
|
||||
Pushes back ("unshifts") a character or integer onto the stream:
|
||||
File.open('t.tmp', 'w') do |f|
|
||||
f.putc('т')
|
||||
f.putc('е')
|
||||
f.putc('с')
|
||||
f.putc('т')
|
||||
end
|
||||
File.read('t.tmp') # => "тест"
|
||||
|
||||
path = 't.tmp'
|
||||
File.write(path, 'foo')
|
||||
File.open(path) do |f|
|
||||
f.ungetc('т')
|
||||
f.read # => "тfoo"
|
||||
end
|
||||
- IO#each_char: Reads each remaining character in the stream,
|
||||
passing the character to the given block:
|
||||
|
||||
Not in \ARGF.
|
||||
File.open('t.rus') do |f|
|
||||
f.pos = 4
|
||||
f.each_char {|c| p c }
|
||||
end
|
||||
|
||||
===== \Method <tt>#putc</tt>
|
||||
Output:
|
||||
|
||||
Writes a character to the stream:
|
||||
|
||||
File.open('t.tmp', 'w') do |f|
|
||||
f.putc('т')
|
||||
f.putc('е')
|
||||
f.putc('с')
|
||||
f.putc('т')
|
||||
end
|
||||
File.read('t.tmp') # => "тест"
|
||||
|
||||
Also in Kernel.
|
||||
|
||||
===== \Method <tt>#each_char</tt>
|
||||
|
||||
Reads each remaining character in the stream,
|
||||
passing the character to the given block:
|
||||
|
||||
File.open('t.rus') do |f|
|
||||
f.pos = 4
|
||||
f.each_char {|c| p c }
|
||||
end
|
||||
|
||||
Output:
|
||||
|
||||
"с"
|
||||
"т"
|
||||
"с"
|
||||
"т"
|
||||
|
||||
=== Byte \IO
|
||||
|
||||
You can process an \IO stream byte-by-byte.
|
||||
You can process an \IO stream byte-by-byte using these methods:
|
||||
|
||||
===== \Method <tt>#getbyte</tt>
|
||||
- IO#getbyte: Returns the next 8-bit byte as an integer in range 0..255:
|
||||
|
||||
Returns the next 8-bit byte as an integer in range 0..255:
|
||||
File.read('t.dat')
|
||||
# => "\xFE\xFF\x99\x90\x99\x91\x99\x92\x99\x93\x99\x94"
|
||||
File.read('t.dat')
|
||||
# => "\xFE\xFF\x99\x90\x99\x91\x99\x92\x99\x93\x99\x94"
|
||||
f = File.new('t.dat')
|
||||
f.getbyte # => 254
|
||||
f.getbyte # => 255
|
||||
f.seek(-2, :END)
|
||||
f.getbyte # => 153
|
||||
f.getbyte # => 148
|
||||
f.getbyte # => nil
|
||||
|
||||
File.read('t.dat')
|
||||
# => "\xFE\xFF\x99\x90\x99\x91\x99\x92\x99\x93\x99\x94"
|
||||
File.read('t.dat')
|
||||
# => "\xFE\xFF\x99\x90\x99\x91\x99\x92\x99\x93\x99\x94"
|
||||
f = File.new('t.dat')
|
||||
f.getbyte # => 254
|
||||
f.getbyte # => 255
|
||||
f.seek(-2, :END)
|
||||
f.getbyte # => 153
|
||||
f.getbyte # => 148
|
||||
f.getbyte # => nil
|
||||
- IO#readbyte (not in \StringIO):
|
||||
Like #getbyte, but raises an exception if at end-of-stream:
|
||||
|
||||
===== \Method <tt>#readbyte</tt>
|
||||
f.readbyte # Raises EOFError.
|
||||
|
||||
Like #getbyte, but raises an exception if at end-of-stream:
|
||||
- IO#ungetbyte (not in \ARGF):
|
||||
Pushes back ("unshifts") a byte back onto the stream:
|
||||
|
||||
f.readbyte # Raises EOFError.
|
||||
f.ungetbyte(0)
|
||||
f.ungetbyte(01)
|
||||
f.read # => "\u0001\u0000"
|
||||
|
||||
Not in \StringIO.
|
||||
- IO#each_byte: Reads each remaining byte in the stream,
|
||||
passing the byte to the given block:
|
||||
|
||||
===== \Method <tt>#ungetbyte</tt>
|
||||
f.seek(-4, :END)
|
||||
f.each_byte {|b| p b }
|
||||
|
||||
Pushes back ("unshifts") a byte back onto the stream:
|
||||
Output:
|
||||
|
||||
f.ungetbyte(0)
|
||||
f.ungetbyte(01)
|
||||
f.read # => "\u0001\u0000"
|
||||
|
||||
Not in \ARGF.
|
||||
|
||||
===== \Method <tt>#each_byte</tt>
|
||||
|
||||
Reads each remaining byte in the stream,
|
||||
passing the byte to the given block:
|
||||
|
||||
f.seek(-4, :END)
|
||||
f.each_byte {|b| p b }
|
||||
|
||||
Output:
|
||||
|
||||
153
|
||||
147
|
||||
153
|
||||
148
|
||||
153
|
||||
147
|
||||
153
|
||||
148
|
||||
|
||||
=== Codepoint \IO
|
||||
|
||||
You can process an \IO stream codepoint-by-codepoint.
|
||||
|
||||
===== \Method +each_codepoint+
|
||||
|
||||
Reads each remaining codepoint in the stream,
|
||||
passing the codepoint to the given block:
|
||||
You can process an \IO stream codepoint-by-codepoint using method
|
||||
+#each_codepoint+:
|
||||
|
||||
a = []
|
||||
File.open('t.rus') do |f|
|
||||
|
|
Loading…
Reference in a new issue