207 int nargin = args.length ();
209 double empty_value = 0.0;
211 if (nargin > 2 && args(nargin-2).is_string ()
212 && args(nargin-2).string_value () ==
"emptyvalue")
214 empty_value = args(nargin-1).double_value ();
219 if (nargin < 1 || nargin > 4)
222 std::istream *input =
nullptr;
223 std::ifstream input_file;
225 if (args(0).is_string ())
228 std::string fname (args(0).string_value ());
230 std::string tname = sys::file_ops::tilde_expand (fname);
234#if defined (OCTAVE_USE_WINDOWS_API)
235 std::wstring wname = sys::u8_to_wstring (tname);
236 input_file.open (wname.c_str (), std::ios::in);
238 input_file.open (tname.c_str (), std::ios::in);
242 error (
"dlmread: unable to open file '%s'", fname.c_str ());
246 else if (args(0).is_scalar_type ())
255 error (
"dlmread: stream FILE not open for input");
258 error (
"dlmread: FILE argument must be a string or file id");
264 if (args(1).is_sq_string ())
267 sep = args(1).string_value ();
279 if (! parse_range_spec (args(2), r0, c0, r1, c1))
280 error (
"dlmread: error parsing RANGE");
282 else if (nargin == 4)
284 r0 = args(2).idx_type_value ();
285 c0 = args(3).idx_type_value ();
288 if (r0 < 0 || c0 < 0)
289 error (
"dlmread: left (R0) and top (C0) must be positive");
292 if (r1 < r0 || c1 < c0)
304 Matrix rdata (rmax, cmax, empty_value);
307 bool iscmplx =
false;
308 bool sep_is_wspace = (sep.find_first_of (
" \t") != std::string::npos);
309 bool auto_sep_is_wspace =
false;
314 const char BOM[3] = {
'\xEF',
'\xBB',
'\xBF'};
317 bool found_bom =
true;
318 for (i_bom = 0; i_bom < 3; i_bom++)
320 char ch_p = input->peek ();
321 if (ch_p == BOM[i_bom])
322 buf[i_bom] = input->get ();
332 for (
int i_ret = i_bom-1; i_ret >= 0; i_ret--)
333 input->putback (buf[i_ret]);
340 char *prev_locale = std::setlocale (LC_ALL,
nullptr);
341 std::string old_locale (prev_locale ? prev_locale :
"");
342 std::setlocale (LC_ALL,
"C");
344 ([old_locale] () { std::setlocale (LC_ALL, old_locale.c_str ()); });
350 while (rcnt > 0 && getline (*input, line))
358 std::istringstream tmp_stream;
361 while (getline (*input, line))
364 if ((! sep_is_wspace || auto_sep_is_wspace)
365 && line.find_first_not_of (
" \t") == std::string::npos)
372 std::size_t pos1 = line.find_first_not_of (
" \t");
376 std::size_t n = line.find_first_of (
",:; \t", pos1);
377 if (n == std::string::npos)
380 auto_sep_is_wspace =
true;
384 char ch = line.at (n);
391 auto_sep_is_wspace =
true;
404 std::size_t pos1, pos2;
405 if (auto_sep_is_wspace)
406 pos1 = line.find_first_not_of (
" \t");
412 pos2 = line.find_first_of (sep, pos1);
414 if (auto_sep_is_wspace && pos2 != std::string::npos)
417 pos2 = line.find_first_not_of (sep, pos2);
418 if (pos2 != std::string::npos)
423 if (pos2 != std::string::npos)
428 while (pos2 != std::string::npos);
433 cdata.
resize (rmax, cmax, empty_value);
435 rdata.
resize (rmax, cmax, empty_value);
438 r = (r > i + 1 ? r : i + 1);
441 std::size_t pos1, pos2;
442 if (auto_sep_is_wspace)
443 pos1 = line.find_first_not_of (
" \t");
451 pos2 = line.find_first_of (sep, pos1);
452 std::string str = line.substr (pos1, pos2 - pos1);
454 if (auto_sep_is_wspace && pos2 != std::string::npos)
457 pos2 = line.find_first_not_of (sep, pos2);
458 if (pos2 != std::string::npos)
461 pos2 = line.length () - 1;
465 if (pos2 == std::string::npos && str.empty ())
468 c = (c > j + 1 ? c : j + 1);
469 if (r > rmax || c > cmax)
473 rmax = std::max (2*(r-1), rmax);
474 cmax = std::max (c, cmax);
476 cdata.
resize (rmax, cmax, empty_value);
478 rdata.
resize (rmax, cmax, empty_value);
481 tmp_stream.str (str);
484 double x = read_value<double> (tmp_stream);
487 if (tmp_stream.eof ())
496 int next_char = tmp_stream.peek ();
497 if (next_char ==
'i' || next_char ==
'j'
498 || next_char ==
'I' || next_char ==
'J')
502 next_char = tmp_stream.peek ();
503 if (next_char == std::istringstream::traits_type::eof ())
519 else if (std::isalpha (next_char) && ! std::isfinite (
x))
526 double y = read_value<double> (tmp_stream);
528 if (! iscmplx && y != 0.0)
549 while (pos2 != std::string::npos);
565 if ((i == 0 && j == 0) || (c0 > c1))
568 cdata = cdata.
extract (0, c0, r1, c1);
573 if ((i == 0 && j == 0) || (c0 > c1))
576 rdata = rdata.
extract (0, c0, r1, c1);