void parse( std::string const& str ) { std::size_t pos = 0; while( pos < str.size() ) { char c = str[pos]; if( c == '[' ) { std::size_t end = str.find_first_of( ']', pos ); if( end != std::string::npos ) { acceptTag( str.substr( pos+1, end-pos-1 ) ); pos = end+1; } else { acceptChar( c ); pos++; } } else { acceptChar( c ); pos++; } } endParse(); }
// Unless the given text is empty, input the text as if it was // entered character by character on the client side, applying // the input mask, if present. WT_USTRING WLineEdit::inputText(const WT_USTRING& text) const { if (!raw_.empty() && !text.empty()) { std::u32string newText = text; std::u32string result = raw_; char32_t chr; bool hadIgnoredChar = false; std::size_t j = 0, i = 0; for (i = 0; i < newText.length(); ++i) { std::size_t previousJ = j; chr = newText[i]; while (j < mask_.length() && !acceptChar(chr, j)) { ++j; /* Try to move forward as long as this characer is not * accepted in this position */ } if (j == mask_.length()) { j = previousJ; hadIgnoredChar = true; } else { if (raw_[j] != chr) { if (case_[j] == '>') { chr = toupper(chr); } else if (case_[j] == '<') { chr = tolower(chr); } result[j] = chr; } ++j; } } if (hadIgnoredChar) { LOG_INFO("Input mask: not all characters in input '" + text + "' complied with " "input mask " + inputMask_ + " and were ignored. Result is '" + result + "'."); } return WT_USTRING(result); } return text; }
static bool matchNext(bool lineStart) { lineStart = !skipUnimportantWhitespace() && lineStart; size_t variadicLength; const SVariadicWordDefinition* variadicWord; size_t constantLength; const SLexConstantsWord* constantWord; if (!getMatches(lineStart, &variadicLength, &variadicWord, &constantLength, &constantWord)) return false; if (constantWord != NULL && constantLength >= variadicLength) { return acceptConstantWord(constantLength, constantWord); } else if (variadicLength > 0) { return acceptVariadic(variadicLength, variadicWord, lineStart); } else { return acceptString() || acceptChar(); } }
bool Reg::accept(string str, bool(*callback)(int code)){ if (!this->isReady)return 0; for (unsigned k = 0; k <= str.length() - 1; k++){ int g = k, now = 0, onacc = -1; while (true){ int t = -1; //accept char finding for (edge *i = DFA.e[now]; i != nullptr; i = i->prev){ if (acceptChar(str[g], i->v)){ t = i->t; g++; break; } } //accept checking if (t != -1) now = t; else{ if (greedy && onacc != -1){ //greedy accept callback(onacc); if (shift){ k = g - 1; } } break; } if (greedy) { if (DFA.acc[now])onacc = DFA.acc[now]; } else if (DFA.acc[now]){ //ungreedy accept callback(DFA.acc[now]); if (shift){ k = g - 1; break; } } } } return 0; }
// Simulates an NFA (non-deterministic finite state automaton) // The states are positions in the input mask. We iterate over // the input string once, going through all of the possible // states in parallel, using the positions and nextPositions vector. bool WLineEdit::validateInputMask() const { std::u32string toCheck = content_; if (toCheck.empty()) { toCheck = raw_; } // Switch between two vectors without copy assignment. std::vector<std::size_t> p1; std::vector<std::size_t> p2; std::vector<std::size_t> *positions = &p1; std::vector<std::size_t> *nextPositions = &p2; positions->push_back(0); for (std::size_t i = 0; i < toCheck.length(); ++i) { for (std::size_t j = 0; j < positions->size(); ++j) { std::size_t currentPosition = (*positions)[j]; if (currentPosition < mask_.length()) { // Check whether we can skip the current position, if so, add // it to positions vector, to be considered later (with the current // input character still). if (SKIPPABLE_MASK_CHARS.find(mask_[currentPosition]) != std::string::npos && (j + 1 == positions->size() || (*positions)[j + 1] != currentPosition + 1)) { positions->push_back(currentPosition + 1); } // Check whether we can accept the current character in the current // position, if so, the next position is added to the nextPositions // vector. if (acceptChar(toCheck[i], currentPosition) && (nextPositions->empty() || nextPositions->back() != currentPosition + 1)) { nextPositions->push_back(currentPosition + 1); } } } std::swap(positions, nextPositions); nextPositions->clear(); if (positions->size() == 0) { return false; } } while (positions->size() > 0) { for (std::size_t j = 0; j < positions->size(); ++j) { std::size_t currentPosition = (*positions)[j]; // One path is in the end state, accept. if (currentPosition == mask_.length()) { return true; } // Check whether we can skip the rest of the mask. if (SKIPPABLE_MASK_CHARS.find(mask_[currentPosition]) != std::string::npos && (nextPositions->empty() || nextPositions->back() != currentPosition + 1)) { nextPositions->push_back(currentPosition + 1); } } std::swap(positions, nextPositions); nextPositions->clear(); } return false; }