string: add character_position function

`character_position` computes the line and column numbers for an
iterator inside a view.
This commit is contained in:
Danny Robson 2018-10-16 18:01:31 +11:00
parent edc245e2d1
commit 6cab42d171

View File

@ -3,16 +3,14 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this * License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. * file, You can obtain one at http://mozilla.org/MPL/2.0/.
* *
* Copyright 2011-2016 Danny Robson <danny@nerdcruft.net> * Copyright 2011-2018 Danny Robson <danny@nerdcruft.net>
*/ */
#ifndef CRUFT_UTIL_STRING_HPP #pragma once
#define CRUFT_UTIL_STRING_HPP
#include "debug.hpp" #include "debug.hpp"
#include "view.hpp" #include "view.hpp"
namespace cruft { namespace cruft {
std::string to_utf8 (const wchar_t*); std::string to_utf8 (const wchar_t*);
std::string to_utf8 (const std::wstring&); std::string to_utf8 (const std::wstring&);
@ -147,7 +145,37 @@ namespace cruft {
{ {
return tokeniser { std::begin (data), std::end (data), separator }; return tokeniser { std::begin (data), std::end (data), separator };
} }
///////////////////////////////////////////////////////////////////////////
/// Calculate the line and column of an iterator within a view.
template <typename IteratorT>
auto
character_position (
cruft::view<IteratorT> data,
IteratorT const cursor
) {
using difference_type = typename std::iterator_traits<IteratorT>::difference_type;
difference_type line_count = 0;
auto current_line = data.begin ();
do {
auto next_line = std::find (current_line, data.end (), '\n');
if (next_line == data.end () || next_line > cursor)
break;
++line_count;
current_line = next_line + 1;
} while (1);
struct {
difference_type line;
difference_type column;
} val = {
.line = line_count,
.column = cursor - current_line,
};
return val;
}
} }
#endif // __UTIL_STRING_HPP