1 /** 2 Utility functions for string processing 3 Copyright: © 2012-2014 RejectedSoftware e.K. 4 License: Subject to the terms of the MIT license, as written in the included LICENSE.txt file. 5 Authors: Sönke Ludwig 6 */ 7 module dmarkdown..string; 8 9 public import std..string; 10 11 import std.algorithm; 12 import std.array; 13 import std.ascii; 14 import std.format; 15 import std.uni; 16 import std.utf; 17 import core.exception; 18 19 20 package: 21 22 /** 23 Checks if all characters in 'str' are contained in 'chars'. 24 */ 25 bool allOf(string str, string chars) 26 @safe pure { 27 foreach (dchar ch; str) 28 if (!chars.canFind(ch)) 29 return false; 30 return true; 31 } 32 33 ptrdiff_t indexOfCT(Char)(in Char[] s, dchar c, CaseSensitive cs = CaseSensitive.yes) 34 @safe pure { 35 if (__ctfe) { 36 if (cs == CaseSensitive.yes) { 37 foreach (i, dchar ch; s) 38 if (ch == c) 39 return i; 40 } else { 41 c = std.uni.toLower(c); 42 foreach (i, dchar ch; s) 43 if (std.uni.toLower(ch) == c) 44 return i; 45 } 46 return -1; 47 } else return std..string.indexOf(s, c, cs); 48 } 49 50 /** 51 Checks if any character in 'str' is contained in 'chars'. 52 */ 53 bool anyOf(string str, string chars) 54 @safe pure { 55 foreach (ch; str) 56 if (chars.canFind(ch)) 57 return true; 58 return false; 59 } 60 61 /** 62 Finds the closing bracket (works with any of '[', '$(LPAREN)', '<', '{'). 63 64 Params: 65 str = input string 66 nested = whether to skip nested brackets 67 Returns: 68 The index of the closing bracket or -1 for unbalanced strings 69 and strings that don't start with a bracket. 70 */ 71 sizediff_t matchBracket(string str, bool nested = true) 72 @safe pure nothrow { 73 if (str.length < 2) return -1; 74 75 char open = str[0], close = void; 76 switch (str[0]) { 77 case '[': close = ']'; break; 78 case '(': close = ')'; break; 79 case '<': close = '>'; break; 80 case '{': close = '}'; break; 81 default: return -1; 82 } 83 84 size_t level = 1; 85 foreach (i, char c; str[1 .. $]) { 86 if (nested && c == open) ++level; 87 else if (c == close) --level; 88 if (level == 0) return i + 1; 89 } 90 return -1; 91 }