Formatting more code with astyle

This commit is contained in:
Strahinja Val Markovic 2013-01-19 20:10:52 -08:00
parent 013a56c25c
commit 4308130ab3
20 changed files with 252 additions and 384 deletions

View File

@ -24,23 +24,18 @@
using boost::algorithm::all;
using boost::algorithm::is_lower;
namespace YouCompleteMe
{
namespace YouCompleteMe {
namespace
{
namespace {
std::string GetWordBoundaryChars( const std::string &text )
{
std::string GetWordBoundaryChars( const std::string &text ) {
std::string result;
for ( uint i = 0; i < text.size(); ++i )
{
for ( uint i = 0; i < text.size(); ++i ) {
if ( i == 0 ||
IsUppercase( text[ i ] ) ||
( i > 0 && text[ i - 1 ] == '_' && isalpha( text[ i ] ) )
)
{
) {
result.push_back( tolower( text[ i ] ) );
}
}
@ -51,11 +46,9 @@ std::string GetWordBoundaryChars( const std::string &text )
} // unnamed namespace
Bitset LetterBitsetFromString( const std::string &text )
{
Bitset LetterBitsetFromString( const std::string &text ) {
Bitset letter_bitset;
foreach ( char letter, text )
{
foreach ( char letter, text ) {
letter_bitset.set( IndexForChar( letter ) );
}
@ -69,19 +62,17 @@ Candidate::Candidate( const std::string &text )
word_boundary_chars_( GetWordBoundaryChars( text ) ),
text_is_lowercase_( all( text, is_lower() ) ),
letters_present_( LetterBitsetFromString( text ) ),
root_node_( new LetterNode( text ) )
{
root_node_( new LetterNode( text ) ) {
}
Result Candidate::QueryMatchResult( const std::string &query ) const
{
Result Candidate::QueryMatchResult( const std::string &query ) const {
LetterNode *node = root_node_.get();
int index_sum = 0;
foreach ( char letter, query )
{
foreach ( char letter, query ) {
const std::list< LetterNode *> *list = node->NodeListForLetter( letter );
if ( !list )
return Result( false );

View File

@ -26,8 +26,7 @@
#include <string>
#include <bitset>
namespace YouCompleteMe
{
namespace YouCompleteMe {
class Result;
@ -35,21 +34,18 @@ typedef std::bitset< NUM_LETTERS > Bitset;
Bitset LetterBitsetFromString( const std::string &text );
class Candidate : boost::noncopyable
{
class Candidate : boost::noncopyable {
public:
explicit Candidate( const std::string &text );
inline const std::string& Text() const
{
inline const std::string &Text() const {
return text_;
}
// Returns true if the candidate contains the bits from the query (it may also
// contain other bits)
inline bool MatchesQueryBitset( const Bitset &query_bitset ) const
{
inline bool MatchesQueryBitset( const Bitset &query_bitset ) const {
return ( letters_present_ & query_bitset ) == query_bitset;
}

View File

@ -26,18 +26,15 @@
# include "CompletionData.h"
#endif // USE_CLANG_COMPLETER
namespace YouCompleteMe
{
namespace YouCompleteMe {
boost::mutex CandidateRepository::singleton_mutex_;
CandidateRepository *CandidateRepository::instance_ = NULL;
CandidateRepository& CandidateRepository::Instance()
{
CandidateRepository &CandidateRepository::Instance() {
boost::lock_guard< boost::mutex > locker( singleton_mutex_ );
if ( !instance_ )
{
if ( !instance_ ) {
static CandidateRepository repo;
instance_ = &repo;
}
@ -46,27 +43,25 @@ CandidateRepository& CandidateRepository::Instance()
}
int CandidateRepository::NumStoredCandidates()
{
int CandidateRepository::NumStoredCandidates() {
boost::lock_guard< boost::mutex > locker( holder_mutex_ );
return candidate_holder_.size();
}
std::vector< const Candidate* > CandidateRepository::GetCandidatesForStrings(
const std::vector< std::string > &strings )
{
std::vector< const Candidate* > candidates;
std::vector< const Candidate * > CandidateRepository::GetCandidatesForStrings(
const std::vector< std::string > &strings ) {
std::vector< const Candidate * > candidates;
candidates.reserve( strings.size() );
{
boost::lock_guard< boost::mutex > locker( holder_mutex_ );
foreach ( const std::string &candidate_text, strings )
{
foreach ( const std::string & candidate_text, strings ) {
const Candidate *&candidate = GetValueElseInsert( candidate_holder_,
candidate_text,
NULL );
if ( !candidate )
candidate = new Candidate( candidate_text );
@ -79,20 +74,19 @@ std::vector< const Candidate* > CandidateRepository::GetCandidatesForStrings(
#ifdef USE_CLANG_COMPLETER
std::vector< const Candidate* > CandidateRepository::GetCandidatesForStrings(
const std::vector< CompletionData > &datas )
{
std::vector< const Candidate* > candidates;
std::vector< const Candidate * > CandidateRepository::GetCandidatesForStrings(
const std::vector< CompletionData > &datas ) {
std::vector< const Candidate * > candidates;
candidates.reserve( datas.size() );
{
boost::lock_guard< boost::mutex > locker( holder_mutex_ );
foreach ( const CompletionData &data, datas )
{
foreach ( const CompletionData & data, datas ) {
const Candidate *&candidate = GetValueElseInsert( candidate_holder_,
data.original_string_,
NULL );
if ( !candidate )
candidate = new Candidate( data.original_string_ );
@ -105,11 +99,9 @@ std::vector< const Candidate* > CandidateRepository::GetCandidatesForStrings(
#endif // USE_CLANG_COMPLETER
CandidateRepository::~CandidateRepository()
{
foreach ( const CandidateHolder::value_type &pair,
candidate_holder_ )
{
CandidateRepository::~CandidateRepository() {
foreach ( const CandidateHolder::value_type & pair,
candidate_holder_ ) {
delete pair.second;
}
}

View File

@ -25,28 +25,26 @@
#include <vector>
#include <string>
namespace YouCompleteMe
{
namespace YouCompleteMe {
class Candidate;
struct CompletionData;
typedef boost::unordered_map< std::string, const Candidate* >
CandidateHolder;
typedef boost::unordered_map< std::string, const Candidate * >
CandidateHolder;
class CandidateRepository : boost::noncopyable
{
class CandidateRepository : boost::noncopyable {
public:
static CandidateRepository& Instance();
static CandidateRepository &Instance();
int NumStoredCandidates();
std::vector< const Candidate* > GetCandidatesForStrings(
const std::vector< std::string > &strings );
std::vector< const Candidate * > GetCandidatesForStrings(
const std::vector< std::string > &strings );
#ifdef USE_CLANG_COMPLETER
std::vector< const Candidate* > GetCandidatesForStrings(
const std::vector< CompletionData > &datas );
std::vector< const Candidate * > GetCandidatesForStrings(
const std::vector< CompletionData > &datas );
#endif // USE_CLANG_COMPLETER
private:

View File

@ -21,8 +21,7 @@
#include <boost/thread.hpp>
#include <boost/utility.hpp>
namespace YouCompleteMe
{
namespace YouCompleteMe {
// This is is basically a multi-consumer single-producer queue, only with the
// twist that we only care about the latest value set. So the GUI thread is the
@ -40,14 +39,12 @@ namespace YouCompleteMe
// nanoseconds it takes to lock a mutex are laughably negligible compared to the
// VimL/Python overhead.
template <typename T>
class ConcurrentLatestValue : boost::noncopyable
{
class ConcurrentLatestValue : boost::noncopyable {
public:
ConcurrentLatestValue() : empty_( true ) {}
void Set( const T& data )
{
void Set( const T &data ) {
{
boost::unique_lock< boost::mutex > lock( mutex_ );
latest_ = data;
@ -57,12 +54,10 @@ public:
condition_variable_.notify_one();
}
T Get()
{
T Get() {
boost::unique_lock< boost::mutex > lock( mutex_ );
while ( empty_ )
{
while ( empty_ ) {
condition_variable_.wait( lock );
}

View File

@ -22,16 +22,13 @@
#include <boost/utility.hpp>
#include <stack>
namespace YouCompleteMe
{
namespace YouCompleteMe {
template <typename T>
class ConcurrentStack : boost::noncopyable
{
class ConcurrentStack : boost::noncopyable {
public:
void Push( const T& data )
{
void Push( const T &data ) {
{
boost::unique_lock< boost::mutex > lock( mutex_ );
stack_.push( data );
@ -40,12 +37,10 @@ public:
condition_variable_.notify_one();
}
T Pop()
{
T Pop() {
boost::unique_lock< boost::mutex > lock( mutex_ );
while ( stack_.empty() )
{
while ( stack_.empty() ) {
condition_variable_.wait( lock );
}

View File

@ -23,30 +23,26 @@
#include <boost/shared_ptr.hpp>
#include <boost/function.hpp>
namespace YouCompleteMe
{
namespace YouCompleteMe {
class Result;
typedef boost::shared_ptr< boost::packaged_task< void > > VoidTask;
template< typename T >
boost::shared_ptr< T > ReturnValueAsShared(
boost::function< T() > func )
{
boost::function< T() > func ) {
return boost::make_shared< T >( func() );
}
template< typename T >
class Future
{
class Future {
public:
Future() {};
Future( boost::shared_future< T > future )
: future_( boost::move( future ) ) {}
bool ResultsReady()
{
bool ResultsReady() {
// It's OK to return true since GetResults will just return a
// default-constructed value if the future_ is uninitialized. If we don't
// return true for this case, any loop waiting on ResultsReady will wait
@ -58,21 +54,17 @@ public:
}
void Wait()
{
void Wait() {
future_.wait();
}
T GetResults()
{
try
{
T GetResults() {
try {
return future_.get();
}
catch ( boost::future_uninitialized & )
{
catch ( boost::future_uninitialized & ) {
// Do nothing and return a T()
}

View File

@ -36,29 +36,22 @@ using boost::shared_ptr;
using boost::bind;
using boost::thread;
namespace YouCompleteMe
{
namespace YouCompleteMe {
typedef boost::function< std::vector< std::string >() >
FunctionReturnsStringVector;
FunctionReturnsStringVector;
extern const unsigned int MAX_ASYNC_THREADS = 4;
extern const unsigned int MIN_ASYNC_THREADS = 2;
namespace
{
namespace {
void QueryThreadMain( IdentifierCompleter::LatestQueryTask &latest_query_task )
{
while ( true )
{
try
{
void QueryThreadMain( IdentifierCompleter::LatestQueryTask &latest_query_task ) {
while ( true ) {
try {
( *latest_query_task.Get() )();
}
catch ( boost::thread_interrupted& )
{
} catch ( boost::thread_interrupted & ) {
return;
}
}
@ -67,16 +60,11 @@ void QueryThreadMain( IdentifierCompleter::LatestQueryTask &latest_query_task )
void BufferIdentifiersThreadMain(
IdentifierCompleter::BufferIdentifiersTaskStack
&buffer_identifiers_task_stack )
{
while ( true )
{
try
{
&buffer_identifiers_task_stack ) {
while ( true ) {
try {
( *buffer_identifiers_task_stack.Pop() )();
}
catch ( boost::thread_interrupted& )
{
} catch ( boost::thread_interrupted & ) {
return;
}
}
@ -88,33 +76,29 @@ void BufferIdentifiersThreadMain(
IdentifierCompleter::IdentifierCompleter()
: candidate_repository_( CandidateRepository::Instance() ),
threading_enabled_( false )
{
threading_enabled_( false ) {
}
IdentifierCompleter::IdentifierCompleter(
const std::vector< std::string > &candidates )
const std::vector< std::string > &candidates )
: candidate_repository_( CandidateRepository::Instance() ),
threading_enabled_( false )
{
threading_enabled_( false ) {
AddCandidatesToDatabase( candidates, "", "" );
}
IdentifierCompleter::IdentifierCompleter(
const std::vector< std::string > &candidates,
const std::string &filetype,
const std::string &filepath )
const std::vector< std::string > &candidates,
const std::string &filetype,
const std::string &filepath )
: candidate_repository_( CandidateRepository::Instance() ),
threading_enabled_( false )
{
threading_enabled_( false ) {
AddCandidatesToDatabase( candidates, filetype, filepath );
}
IdentifierCompleter::~IdentifierCompleter()
{
IdentifierCompleter::~IdentifierCompleter() {
query_threads_.interrupt_all();
query_threads_.join_all();
@ -125,22 +109,20 @@ IdentifierCompleter::~IdentifierCompleter()
// We need this mostly so that we can not use it in tests. Apparently the
// GoogleTest framework goes apeshit on us if we enable threads by default.
void IdentifierCompleter::EnableThreading()
{
void IdentifierCompleter::EnableThreading() {
threading_enabled_ = true;
InitThreads();
}
void IdentifierCompleter::AddCandidatesToDatabase(
const std::vector< std::string > &new_candidates,
const std::string &filetype,
const std::string &filepath )
{
const std::vector< std::string > &new_candidates,
const std::string &filetype,
const std::string &filepath ) {
std::list< const Candidate *> &candidates =
GetCandidateList( filetype, filepath );
std::vector< const Candidate* > repository_candidates =
std::vector< const Candidate * > repository_candidates =
candidate_repository_.GetCandidatesForStrings( new_candidates );
candidates.insert( candidates.end(),
@ -150,24 +132,22 @@ void IdentifierCompleter::AddCandidatesToDatabase(
void IdentifierCompleter::AddCandidatesToDatabaseFromBuffer(
const std::string &buffer_contents,
const std::string &filetype,
const std::string &filepath )
{
const std::string &buffer_contents,
const std::string &filetype,
const std::string &filepath ) {
ClearCandidatesStoredForFile( filetype, filepath );
AddCandidatesToDatabase(
ExtractIdentifiersFromText( RemoveIdentifierFreeText( buffer_contents ) ),
filetype,
filepath );
ExtractIdentifiersFromText( RemoveIdentifierFreeText( buffer_contents ) ),
filetype,
filepath );
}
void IdentifierCompleter::AddCandidatesToDatabaseFromBufferAsync(
std::string buffer_contents,
std::string filetype,
std::string filepath )
{
std::string buffer_contents,
std::string filetype,
std::string filepath ) {
// TODO: throw exception when threading is not enabled and this is called
if ( !threading_enabled_ )
return;
@ -180,29 +160,26 @@ void IdentifierCompleter::AddCandidatesToDatabaseFromBufferAsync(
boost::move( filepath ) );
buffer_identifiers_task_stack_.Push(
make_shared< packaged_task< void > >( functor ) );
make_shared< packaged_task< void > >( functor ) );
}
std::vector< std::string > IdentifierCompleter::CandidatesForQuery(
const std::string &query ) const
{
const std::string &query ) const {
return CandidatesForQueryAndType( query, "" );
}
std::vector< std::string > IdentifierCompleter::CandidatesForQueryAndType(
const std::string &query,
const std::string &filetype ) const
{
const std::string &query,
const std::string &filetype ) const {
std::vector< Result > results;
ResultsForQueryAndType( query, filetype, results );
std::vector< std::string > candidates;
candidates.reserve( results.size() );
foreach ( const Result& result, results )
{
foreach ( const Result & result, results ) {
candidates.push_back( *result.Text() );
}
return candidates;
@ -210,9 +187,8 @@ std::vector< std::string > IdentifierCompleter::CandidatesForQueryAndType(
Future< AsyncResults > IdentifierCompleter::CandidatesForQueryAndTypeAsync(
const std::string &query,
const std::string &filetype ) const
{
const std::string &query,
const std::string &filetype ) const {
// TODO: throw exception when threading is not enabled and this is called
if ( !threading_enabled_ )
return Future< AsyncResults >();
@ -224,8 +200,8 @@ Future< AsyncResults > IdentifierCompleter::CandidatesForQueryAndTypeAsync(
filetype );
QueryTask task = make_shared< packaged_task< AsyncResults > >(
bind( ReturnValueAsShared< std::vector< std::string > >,
functor ) );
bind( ReturnValueAsShared< std::vector< std::string > >,
functor ) );
unique_future< AsyncResults > future = task->get_future();
@ -235,24 +211,22 @@ Future< AsyncResults > IdentifierCompleter::CandidatesForQueryAndTypeAsync(
void IdentifierCompleter::ResultsForQueryAndType(
const std::string &query,
const std::string &filetype,
std::vector< Result > &results ) const
{
const std::string &query,
const std::string &filetype,
std::vector< Result > &results ) const {
FiletypeMap::const_iterator it = filetype_map_.find( filetype );
if ( it == filetype_map_.end() || query.empty() )
return;
Bitset query_bitset = LetterBitsetFromString( query );
boost::unordered_set< const Candidate* > seen_candidates;
boost::unordered_set< const Candidate * > seen_candidates;
seen_candidates.reserve( candidate_repository_.NumStoredCandidates() );
foreach ( const FilepathToCandidates::value_type &path_and_candidates,
*it->second )
{
foreach ( const Candidate* candidate, *path_and_candidates.second )
{
foreach ( const FilepathToCandidates::value_type & path_and_candidates,
*it->second ) {
foreach ( const Candidate * candidate, *path_and_candidates.second ) {
if ( ContainsKey( seen_candidates, candidate ) )
continue;
else
@ -262,6 +236,7 @@ void IdentifierCompleter::ResultsForQueryAndType(
continue;
Result result = candidate->QueryMatchResult( query );
if ( result.IsSubsequence() )
results.push_back( result );
}
@ -272,48 +247,44 @@ void IdentifierCompleter::ResultsForQueryAndType(
void IdentifierCompleter::ClearCandidatesStoredForFile(
const std::string &filetype,
const std::string &filepath )
{
const std::string &filetype,
const std::string &filepath ) {
GetCandidateList( filetype, filepath ).clear();
}
std::list< const Candidate* >& IdentifierCompleter::GetCandidateList(
const std::string &filetype,
const std::string &filepath )
{
std::list< const Candidate * > &IdentifierCompleter::GetCandidateList(
const std::string &filetype,
const std::string &filepath ) {
boost::shared_ptr< FilepathToCandidates > &path_to_candidates =
filetype_map_[ filetype ];
if ( !path_to_candidates )
path_to_candidates.reset( new FilepathToCandidates() );
boost::shared_ptr< std::list< const Candidate* > > &candidates =
(*path_to_candidates)[ filepath ];
boost::shared_ptr< std::list< const Candidate * > > &candidates =
( *path_to_candidates )[ filepath ];
if ( !candidates )
candidates.reset( new std::list< const Candidate* >() );
candidates.reset( new std::list< const Candidate * >() );
return *candidates;
}
void IdentifierCompleter::InitThreads()
{
void IdentifierCompleter::InitThreads() {
int query_threads_to_create =
std::max( MIN_ASYNC_THREADS,
std::min( MAX_ASYNC_THREADS, thread::hardware_concurrency() ) );
std::min( MAX_ASYNC_THREADS, thread::hardware_concurrency() ) );
for ( int i = 0; i < query_threads_to_create; ++i )
{
for ( int i = 0; i < query_threads_to_create; ++i ) {
query_threads_.create_thread( bind( QueryThreadMain,
boost::ref( latest_query_task_ ) ) );
}
buffer_identifiers_thread_ = boost::thread(
BufferIdentifiersThreadMain,
boost::ref( buffer_identifiers_task_stack_ ) );
BufferIdentifiersThreadMain,
boost::ref( buffer_identifiers_task_stack_ ) );
}

View File

@ -30,8 +30,7 @@
#include <string>
namespace YouCompleteMe
{
namespace YouCompleteMe {
class Candidate;
class CandidateRepository;
@ -39,23 +38,22 @@ class CandidateRepository;
typedef boost::shared_ptr< std::vector< std::string > > AsyncResults;
class IdentifierCompleter : boost::noncopyable
{
class IdentifierCompleter : boost::noncopyable {
public:
IdentifierCompleter();
IdentifierCompleter( const std::vector< std::string > &candidates );
IdentifierCompleter( const std::vector< std::string > &candidates,
const std::string &filetype,
const std::string &filepath );
const std::string &filetype,
const std::string &filepath );
~IdentifierCompleter();
void EnableThreading();
void AddCandidatesToDatabase(
const std::vector< std::string > &new_candidates,
const std::string &filetype,
const std::string &filepath );
const std::vector< std::string > &new_candidates,
const std::string &filetype,
const std::string &filepath );
void AddCandidatesToDatabaseFromBuffer( const std::string &buffer_contents,
const std::string &filetype,
@ -65,24 +63,24 @@ public:
// avoid an expensive copy of buffer_contents if the param is taken by value
// (move ctors FTW)
void AddCandidatesToDatabaseFromBufferAsync(
std::string buffer_contents,
std::string filetype,
std::string filepath );
std::string buffer_contents,
std::string filetype,
std::string filepath );
// Only provided for tests!
std::vector< std::string > CandidatesForQuery(
const std::string &query ) const;
const std::string &query ) const;
std::vector< std::string > CandidatesForQueryAndType(
const std::string &query,
const std::string &filetype ) const;
const std::string &query,
const std::string &filetype ) const;
Future< AsyncResults > CandidatesForQueryAndTypeAsync(
const std::string &query,
const std::string &filetype ) const;
const std::string &query,
const std::string &filetype ) const;
typedef boost::shared_ptr<
boost::packaged_task< AsyncResults > > QueryTask;
typedef boost::shared_ptr <
boost::packaged_task< AsyncResults > > QueryTask;
typedef ConcurrentLatestValue< QueryTask > LatestQueryTask;
@ -97,21 +95,21 @@ private:
void ClearCandidatesStoredForFile( const std::string &filetype,
const std::string &filepath );
std::list< const Candidate* >& GetCandidateList(
const std::string &filetype,
const std::string &filepath );
std::list< const Candidate * > &GetCandidateList(
const std::string &filetype,
const std::string &filepath );
void InitThreads();
// filepath -> *( *candidate )
typedef boost::unordered_map< std::string,
boost::shared_ptr< std::list< const Candidate* > > >
FilepathToCandidates;
typedef boost::unordered_map < std::string,
boost::shared_ptr< std::list< const Candidate * > > >
FilepathToCandidates;
// filetype -> *( filepath -> *( *candidate ) )
typedef boost::unordered_map< std::string,
boost::shared_ptr< FilepathToCandidates > > FiletypeMap;
typedef boost::unordered_map < std::string,
boost::shared_ptr< FilepathToCandidates > > FiletypeMap;

View File

@ -21,10 +21,9 @@
#include <boost/regex.hpp>
#include <boost/algorithm/string/regex.hpp>
namespace YouCompleteMe
{
namespace YouCompleteMe {
const char* COMMENT_AND_STRING_REGEX =
const char *COMMENT_AND_STRING_REGEX =
"//.*?$" // Anything following '//'
"|"
"#.*?$" // Anything following '#'
@ -35,19 +34,17 @@ const char* COMMENT_AND_STRING_REGEX =
"|"
"\"[^\"]*\""; // Anything inside double quotes, "..."
const char* IDENTIFIER_REGEX = "[_a-zA-Z]\\w*";
const char *IDENTIFIER_REGEX = "[_a-zA-Z]\\w*";
std::string RemoveIdentifierFreeText( std::string text )
{
std::string RemoveIdentifierFreeText( std::string text ) {
boost::erase_all_regex( text, boost::regex( COMMENT_AND_STRING_REGEX ) );
return text;
}
std::vector< std::string > ExtractIdentifiersFromText(
const std::string &text )
{
const std::string &text ) {
std::string::const_iterator start = text.begin();
std::string::const_iterator end = text.end();
@ -55,8 +52,8 @@ std::vector< std::string > ExtractIdentifiersFromText(
boost::regex expression( IDENTIFIER_REGEX );
std::vector< std::string > identifiers;
while ( boost::regex_search( start, end, matches, expression ) )
{
while ( boost::regex_search( start, end, matches, expression ) ) {
identifiers.push_back( matches[ 0 ] );
start = matches[ 0 ].second;
}

View File

@ -21,8 +21,7 @@
#include <vector>
#include <string>
namespace YouCompleteMe
{
namespace YouCompleteMe {
// NOTE: this function accepts the text param by value on purpose; it internally
// needs a copy before processing the text so the copy might as well be made on
@ -32,7 +31,7 @@ namespace YouCompleteMe
std::string RemoveIdentifierFreeText( std::string text );
std::vector< std::string > ExtractIdentifiersFromText(
const std::string &text );
const std::string &text );
} // namespace YouCompleteMe

View File

@ -19,14 +19,12 @@
#include "standard.h"
namespace YouCompleteMe
{
namespace YouCompleteMe {
LetterNode::LetterNode( char letter, int index )
: is_uppercase_( IsUppercase( letter ) ),
is_root_node_( false ),
index_( index )
{
index_( index ) {
}
@ -34,12 +32,10 @@ LetterNode::LetterNode( char letter, int index )
LetterNode::LetterNode( const std::string &text )
: is_uppercase_( false ),
is_root_node_( true ),
index_( -1 )
{
index_( -1 ) {
letternode_per_text_index_.resize( text.size() );
for ( uint i = 0; i < text.size(); ++i)
{
for ( uint i = 0; i < text.size(); ++i ) {
char letter = text[ i ];
LetterNode *node = new LetterNode( letter, i );
letters_[ letter ].push_back( node );
@ -47,12 +43,10 @@ LetterNode::LetterNode( const std::string &text )
}
for ( int i = static_cast< int >( letternode_per_text_index_.size() ) - 1;
i >= 0; --i )
{
i >= 0; --i ) {
LetterNode *node_to_add = letternode_per_text_index_[ i ].get();
for ( int j = i - 1; j >= 0; --j )
{
for ( int j = i - 1; j >= 0; --j ) {
letternode_per_text_index_[ j ]->PrependNodeForLetter( text[ i ],
node_to_add );
}

View File

@ -28,36 +28,30 @@
#include <string>
namespace YouCompleteMe
{
namespace YouCompleteMe {
class LetterNode : boost::noncopyable
{
class LetterNode : boost::noncopyable {
public:
explicit LetterNode( char letter, int index );
explicit LetterNode( char letter, int index );
// this is for root nodes
explicit LetterNode( const std::string &text );
explicit LetterNode( const std::string &text );
inline bool LetterIsUppercase() const
{
inline bool LetterIsUppercase() const {
return is_uppercase_;
}
inline const std::list< LetterNode* >* NodeListForLetter( char letter )
{
inline const std::list< LetterNode * > *NodeListForLetter( char letter ) {
return letters_.ListPointerAt( letter );
}
inline void PrependNodeForLetter( char letter, LetterNode* node )
{
inline void PrependNodeForLetter( char letter, LetterNode *node ) {
letters_[ letter ].push_front( node );
}
inline int Index()
{
inline int Index() {
return index_;
}
@ -65,9 +59,9 @@ private:
LetterNodeListMap letters_;
std::vector< boost::shared_ptr< LetterNode > > letternode_per_text_index_;
bool is_uppercase_;
bool is_root_node_;
int index_;
bool is_uppercase_;
bool is_root_node_;
int index_;
};
} // namespace YouCompleteMe

View File

@ -18,22 +18,19 @@
#include "LetterNodeListMap.h"
#include "standard.h"
namespace YouCompleteMe
{
namespace YouCompleteMe {
const int kNumLetters = NUM_LETTERS;
static const int kLettersIndexStart = 0;
static const int kNumbersIndexStart = 26;
bool IsUppercase( char letter )
{
bool IsUppercase( char letter ) {
return 'A' <= letter && letter <= 'Z';
}
int IndexForChar( char letter )
{
int IndexForChar( char letter ) {
if ( IsUppercase( letter ) )
return letter + ( 'a' - 'A' );
@ -41,55 +38,48 @@ int IndexForChar( char letter )
}
LetterNodeListMap::LetterNodeListMap()
{
LetterNodeListMap::LetterNodeListMap() {
letters_.resize( kNumLetters );
for ( uint i = 0; i < letters_.size(); ++i )
{
for ( uint i = 0; i < letters_.size(); ++i ) {
letters_[ i ] = NULL;
}
}
LetterNodeListMap::~LetterNodeListMap()
{
for ( uint i = 0; i < letters_.size(); ++i )
{
LetterNodeListMap::~LetterNodeListMap() {
for ( uint i = 0; i < letters_.size(); ++i ) {
delete letters_[ i ];
}
}
bool LetterNodeListMap::HasLetter( char letter )
{
bool LetterNodeListMap::HasLetter( char letter ) {
int letter_index = IndexForChar( letter );
std::list< LetterNode* > *list = letters_[ letter_index ];
std::list< LetterNode * > *list = letters_[ letter_index ];
return list;
}
std::list< LetterNode* >& LetterNodeListMap::operator[] ( char letter )
{
std::list< LetterNode * > &LetterNodeListMap::operator[] ( char letter ) {
int letter_index = IndexForChar( letter );
std::list< LetterNode* > *list = letters_[ letter_index ];
std::list< LetterNode * > *list = letters_[ letter_index ];
if ( list )
return *list;
letters_[ letter_index ] = new std::list< LetterNode* >();
letters_[ letter_index ] = new std::list< LetterNode * >();
return *letters_[ letter_index ];
}
std::list< LetterNode* >* LetterNodeListMap::ListPointerAt( char letter )
{
std::list< LetterNode * > *LetterNodeListMap::ListPointerAt( char letter ) {
return letters_[ IndexForChar( letter ) ];
}
bool LetterNodeListMap::HasLetter( char letter ) const
{
bool LetterNodeListMap::HasLetter( char letter ) const {
return letters_[ IndexForChar( letter ) ] != NULL;
}

View File

@ -24,8 +24,7 @@
#define NUM_LETTERS 128
namespace YouCompleteMe
{
namespace YouCompleteMe {
class LetterNode;
@ -34,23 +33,22 @@ extern const int kNumLetters;
int IndexForChar( char letter );
bool IsUppercase( char letter );
class LetterNodeListMap : boost::noncopyable
{
class LetterNodeListMap : boost::noncopyable {
public:
LetterNodeListMap();
~LetterNodeListMap();
bool HasLetter( char letter );
std::list< LetterNode* >& operator[] ( char letter );
std::list< LetterNode * > &operator[] ( char letter );
std::list< LetterNode* >* ListPointerAt( char letter );
std::list< LetterNode * > *ListPointerAt( char letter );
bool HasLetter( char letter ) const;
private:
std::vector< std::list< LetterNode* >* > letters_;
std::vector< std::list< LetterNode * >* > letters_;
};
} // namespace YouCompleteMe

View File

@ -23,15 +23,12 @@
using boost::algorithm::istarts_with;
namespace YouCompleteMe
{
namespace YouCompleteMe {
namespace
{
namespace {
int LongestCommonSubsequenceLength( const std::string &first,
const std::string &second )
{
const std::string &second ) {
const std::string &longer = first.size() > second.size() ? first : second;
const std::string &shorter = first.size() > second.size() ? second : first;
@ -41,18 +38,15 @@ int LongestCommonSubsequenceLength( const std::string &first,
std::vector<int> previous( shorter_len + 1, 0 );
std::vector<int> current( shorter_len + 1, 0 );
for (int i = 0; i < longer_len; ++i )
{
for (int j = 0; j < shorter_len; ++j )
{
for ( int i = 0; i < longer_len; ++i ) {
for ( int j = 0; j < shorter_len; ++j ) {
if ( toupper( longer[ i ] ) == toupper( shorter[ j ] ) )
current[ j + 1 ] = previous[ j ] + 1;
else
current[ j + 1 ] = std::max( current[ j ], previous[ j + 1 ] );
}
for (int j = 0; j < shorter_len; ++j )
{
for ( int j = 0; j < shorter_len; ++j ) {
previous[ j + 1 ] = current[ j + 1 ];
}
}
@ -62,9 +56,8 @@ int LongestCommonSubsequenceLength( const std::string &first,
int NumWordBoundaryCharMatches( const std::string &query,
const std::string &word_boundary_chars )
{
return LongestCommonSubsequenceLength(query, word_boundary_chars);
const std::string &word_boundary_chars ) {
return LongestCommonSubsequenceLength( query, word_boundary_chars );
}
} // unnamed namespace
@ -79,8 +72,7 @@ Result::Result()
query_is_candidate_prefix_( false ),
text_is_lowercase_( false ),
char_match_index_sum_( 0 ),
text_( NULL )
{
text_( NULL ) {
}
@ -94,8 +86,7 @@ Result::Result( bool is_subsequence )
query_is_candidate_prefix_( false ),
text_is_lowercase_( false ),
char_match_index_sum_( 0 ),
text_( NULL )
{
text_( NULL ) {
}
@ -114,66 +105,57 @@ Result::Result( bool is_subsequence,
query_is_candidate_prefix_( false ),
text_is_lowercase_( text_is_lowercase ),
char_match_index_sum_( char_match_index_sum ),
text_( text )
{
text_( text ) {
if ( is_subsequence )
SetResultFeaturesFromQuery( word_boundary_chars, query );
}
bool Result::operator< ( const Result &other ) const
{
bool Result::operator< ( const Result &other ) const {
// Yes, this is ugly but it also needs to be fast. Since this is called a
// bazillion times, we have to make sure only the required comparisons are
// made, and no more.
if ( !query_is_empty_ )
{
if ( !query_is_empty_ ) {
if ( first_char_same_in_query_and_text_ !=
other.first_char_same_in_query_and_text_ )
{
other.first_char_same_in_query_and_text_ ) {
return first_char_same_in_query_and_text_;
}
bool equal_wb_ratios = AlmostEqual(
ratio_of_word_boundary_chars_in_query_,
other.ratio_of_word_boundary_chars_in_query_ );
ratio_of_word_boundary_chars_in_query_,
other.ratio_of_word_boundary_chars_in_query_ );
bool equal_wb_utilization = AlmostEqual(
word_boundary_char_utilization_,
other.word_boundary_char_utilization_ );
word_boundary_char_utilization_,
other.word_boundary_char_utilization_ );
if ( AlmostEqual( ratio_of_word_boundary_chars_in_query_, 1.0 ) ||
AlmostEqual( other.ratio_of_word_boundary_chars_in_query_, 1.0 ) )
{
if ( !equal_wb_ratios )
{
AlmostEqual( other.ratio_of_word_boundary_chars_in_query_, 1.0 ) ) {
if ( !equal_wb_ratios ) {
return ratio_of_word_boundary_chars_in_query_ >
other.ratio_of_word_boundary_chars_in_query_;
other.ratio_of_word_boundary_chars_in_query_;
}
else
{
else {
if ( !equal_wb_utilization )
return word_boundary_char_utilization_ >
other.word_boundary_char_utilization_;
other.word_boundary_char_utilization_;
}
}
if ( query_is_candidate_prefix_ != other.query_is_candidate_prefix_ )
return query_is_candidate_prefix_;
if ( !equal_wb_ratios )
{
if ( !equal_wb_ratios ) {
return ratio_of_word_boundary_chars_in_query_ >
other.ratio_of_word_boundary_chars_in_query_;
other.ratio_of_word_boundary_chars_in_query_;
}
else
{
else {
if ( !equal_wb_utilization )
return word_boundary_char_utilization_ >
other.word_boundary_char_utilization_;
other.word_boundary_char_utilization_;
}
if ( char_match_index_sum_ != other.char_match_index_sum_ )
@ -192,16 +174,15 @@ bool Result::operator< ( const Result &other ) const
void Result::SetResultFeaturesFromQuery(
const std::string &word_boundary_chars,
const std::string &query)
{
const std::string &word_boundary_chars,
const std::string &query ) {
query_is_empty_ = query.empty();
if ( query.empty() || text_->empty() )
return;
first_char_same_in_query_and_text_ =
toupper( query[ 0 ] ) == toupper( (*text_)[ 0 ] );
toupper( query[ 0 ] ) == toupper( ( *text_ )[ 0 ] );
int num_wb_matches = NumWordBoundaryCharMatches( query,
word_boundary_chars );
ratio_of_word_boundary_chars_in_query_ =

View File

@ -20,11 +20,9 @@
#include <string>
namespace YouCompleteMe
{
namespace YouCompleteMe {
class Result
{
class Result {
public:
Result();
explicit Result( bool is_subsequence );
@ -38,20 +36,18 @@ public:
bool operator< ( const Result &other ) const;
inline bool IsSubsequence() const
{
inline bool IsSubsequence() const {
return is_subsequence_;
}
inline const std::string* Text() const
{
inline const std::string *Text() const {
return text_;
}
private:
void SetResultFeaturesFromQuery(
const std::string &query,
const std::string &word_boundary_chars );
const std::string &query,
const std::string &word_boundary_chars );
// true when the query for which the result was created was an empty string;
// in these cases we just use a lexicographic comparison

View File

@ -23,32 +23,28 @@
namespace fs = boost::filesystem;
namespace YouCompleteMe
{
namespace YouCompleteMe {
bool AlmostEqual( double a, double b )
{
bool AlmostEqual( double a, double b ) {
return std::abs( a - b ) <=
( std::numeric_limits< double >::epsilon() *
std::max( std::abs( a ), std::abs( b ) ) );
( std::numeric_limits< double >::epsilon() *
std::max( std::abs( a ), std::abs( b ) ) );
}
std::string ReadUtf8File( const fs::path &filepath )
{
fs::ifstream file( filepath, std::ios::in | std::ios::binary );
std::vector< char > contents( (std::istreambuf_iterator< char >( file )),
std::istreambuf_iterator< char >() );
std::string ReadUtf8File( const fs::path &filepath ) {
fs::ifstream file( filepath, std::ios::in | std::ios::binary );
std::vector< char > contents( ( std::istreambuf_iterator< char >( file ) ),
std::istreambuf_iterator< char >() );
if ( contents.size() == 0 )
return std::string();
if ( contents.size() == 0 )
return std::string();
return std::string( contents.begin(), contents.end() );
return std::string( contents.begin(), contents.end() );
}
void WriteUtf8File( const fs::path &filepath, const std::string &contents )
{
void WriteUtf8File( const fs::path &filepath, const std::string &contents ) {
fs::ofstream file;
file.open( filepath );
file << contents;

View File

@ -23,8 +23,7 @@
#include <boost/filesystem.hpp>
namespace fs = boost::filesystem;
namespace YouCompleteMe
{
namespace YouCompleteMe {
bool AlmostEqual( double a, double b );
@ -40,16 +39,14 @@ template <class Container, class Key>
typename Container::mapped_type &
GetValueElseInsert( Container &container,
const Key &key,
const typename Container::mapped_type &value )
{
const typename Container::mapped_type &value ) {
return container.insert( typename Container::value_type( key, value ) )
.first->second;
.first->second;
}
template <class Container, class Key>
bool ContainsKey( Container &container, const Key &key )
{
bool ContainsKey( Container &container, const Key &key ) {
return container.find( key ) != container.end();
}
@ -58,22 +55,21 @@ template <class Container, class Key>
typename Container::mapped_type
FindWithDefault( Container &container,
const Key &key,
const typename Container::mapped_type &value )
{
const typename Container::mapped_type &value ) {
typename Container::iterator it = container.find( key );
return it != container.end() ? it->second : value;
}
template <class Container, class Key>
bool Erase( Container &container, const Key &key )
{
bool Erase( Container &container, const Key &key ) {
typename Container::iterator it = container.find( key );
if ( it != container.end() )
{
if ( it != container.end() ) {
container.erase( it );
return true;
}
return false;
}

View File

@ -20,8 +20,7 @@
#include <boost/exception/all.hpp>
namespace YouCompleteMe
{
namespace YouCompleteMe {
#define boost_throw(x) BOOST_THROW_EXCEPTION(x)