├── README.md ├── CharacterClasses ├── MatchingUnicodeRanges.js ├── Slides │ ├── 3. Ranges.pdf │ ├── 6. Shorthand Character Classes.pdf │ ├── 2. Working With Character Classes.pdf │ ├── 7. Negated Shorthand Character Classes.pdf │ └── 4. Character Classes And Metacharacters.pdf ├── MetacharactersAndClasses.js ├── UnicodeRange.js ├── Ranges.js ├── CharacterClasses.js └── NegatedCharacterClasses.js ├── Quantifiers ├── ZeroOrMore.js ├── GreedyOrLazy.js ├── ExactQuantity.js ├── Slides │ ├── 8. Challenges.pdf │ ├── 7. Greedy Vs Lazy.pdf │ ├── 3. Quantifiers Zero Or One Of.pdf │ ├── 4. Quantifiers One Or More Of.pdf │ ├── 5. Quantifiers Zero Or More Of.pdf │ ├── 11. Challenge 3# Matching E-mail.pdf │ ├── 10. Challenge 2# Matching Phone Number.pdf │ ├── 6. Quantifier {n, M} (matches Exactly N).pdf │ └── 9. Challenge 1# Matching Social Security Number.pdf ├── OneOrMoreOf.js ├── PhoneNumber.js ├── SocialSecurityNumber.js └── Emails.js ├── Characters ├── Slides │ ├── 3. Flags.pdf │ ├── 12. Wrap Up.pdf │ ├── 2. Hello Regex.pdf │ ├── 6. Metacharacters.pdf │ ├── 5 Escape Sequences.pdf │ ├── 11. Unicode Matching.pdf │ ├── 4. Exploring The Api.pdf │ ├── 9. Metacharacters Pipe.pdf │ ├── 10. RegExp Or Regex Literal.pdf │ ├── 8. Selecting White Spaces.pdf │ └── 7. Metacharacters Any Single Character.pdf ├── DotAll.js ├── AnyWhiteSpace.js ├── UnicodeMatching.js ├── RegexpOrRegexLiteral.js ├── Metacharacters.js ├── LiteralVsRegExp.js ├── HelloRegex.js ├── AnySingleCharacter.js ├── Flags.js ├── SimpleCharacters.js ├── AlternationOperator.js ├── MatchingCharacters.js ├── ExploringTheAPI.js └── EscapeSequences.js ├── Groups ├── Slides │ ├── 2. Using Groups.pdf │ ├── 5. Nested Groups.pdf │ ├── 6. Named Groups.pdf │ ├── 8. Special Groups Lookahead.pdf │ ├── 9. Special Groups Lookbehind.pdf │ ├── 4. Backreference & Replace Method.pdf │ └── 3. Capturing & Non-capturing Group.pdf ├── NestedGroups.js ├── NamedCapturingGroups.js ├── CapturingAndNonCapturing.js ├── Lookbehind.js ├── BackreferencesAndReplace.js ├── Lookahead.js └── WorkingWithGroups.js ├── Anchors ├── Slides │ ├── 2. Using Anchors.pdf │ ├── 3. Using Boundaries.pdf │ ├── 5. Using Multiline Flag.pdf │ └── 4. Implementing Dotall In Js.pdf ├── WordBondaries.js ├── Anchors.js ├── DotAll.js └── MultilineFlag.js ├── Recipes ├── Slides │ ├── 4. Matching Zip Code.pdf │ ├── 7. Password Validation.pdf │ ├── 5. Matching Number Ranges.pdf │ ├── 6. Matching Ipv4 Addresses.pdf │ └── 2. Applying Syntax Highlight #01.pdf ├── zip-code │ └── ZipCode.js ├── NumberRanges │ └── NumberRanges.js ├── password-validation │ └── PasswordValidation.js ├── ipv4 │ └── IPv4.js └── syntax-highlight │ ├── utils │ ├── files.js │ └── Highlighter.js │ ├── src │ └── sourceCode.html │ ├── SyntaxHighlight.js │ └── modified │ └── styledSourceCode.html ├── Bonus └── Cheatsheet.md └── Cheatsheet.md /README.md: -------------------------------------------------------------------------------- 1 | # regex-course -------------------------------------------------------------------------------- /CharacterClasses/MatchingUnicodeRanges.js: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Quantifiers/ZeroOrMore.js: -------------------------------------------------------------------------------- 1 | const sentence = "1 10 100 1000..." 2 | console.log(sentence.match(/10*/g)); -------------------------------------------------------------------------------- /Quantifiers/GreedyOrLazy.js: -------------------------------------------------------------------------------- 1 | const sentence = '

Hello World!

' 2 | console.log(sentence.match(/<.+?>/)); -------------------------------------------------------------------------------- /Quantifiers/ExactQuantity.js: -------------------------------------------------------------------------------- 1 | const sentence = "www.youtube.com" 2 | console.log(sentence.match(/w{3}\.\w+.\w{3}/g)); -------------------------------------------------------------------------------- /Characters/Slides/3. Flags.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/3. Flags.pdf -------------------------------------------------------------------------------- /Characters/Slides/12. Wrap Up.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/12. Wrap Up.pdf -------------------------------------------------------------------------------- /Groups/Slides/2. Using Groups.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Groups/Slides/2. Using Groups.pdf -------------------------------------------------------------------------------- /Groups/Slides/5. Nested Groups.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Groups/Slides/5. Nested Groups.pdf -------------------------------------------------------------------------------- /Groups/Slides/6. Named Groups.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Groups/Slides/6. Named Groups.pdf -------------------------------------------------------------------------------- /Anchors/Slides/2. Using Anchors.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Anchors/Slides/2. Using Anchors.pdf -------------------------------------------------------------------------------- /Characters/Slides/2. Hello Regex.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/2. Hello Regex.pdf -------------------------------------------------------------------------------- /Quantifiers/Slides/8. Challenges.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Quantifiers/Slides/8. Challenges.pdf -------------------------------------------------------------------------------- /Anchors/Slides/3. Using Boundaries.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Anchors/Slides/3. Using Boundaries.pdf -------------------------------------------------------------------------------- /CharacterClasses/Slides/3. Ranges.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/CharacterClasses/Slides/3. Ranges.pdf -------------------------------------------------------------------------------- /Characters/DotAll.js: -------------------------------------------------------------------------------- 1 | const sentence = `Hello World\r!` 2 | const regex = /World./ // dotAll 3 | console.log(sentence.match(regex)); 4 | -------------------------------------------------------------------------------- /Characters/Slides/6. Metacharacters.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/6. Metacharacters.pdf -------------------------------------------------------------------------------- /Recipes/Slides/4. Matching Zip Code.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Recipes/Slides/4. Matching Zip Code.pdf -------------------------------------------------------------------------------- /Characters/Slides/5 Escape Sequences.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/5 Escape Sequences.pdf -------------------------------------------------------------------------------- /Quantifiers/Slides/7. Greedy Vs Lazy.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Quantifiers/Slides/7. Greedy Vs Lazy.pdf -------------------------------------------------------------------------------- /Recipes/Slides/7. Password Validation.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Recipes/Slides/7. Password Validation.pdf -------------------------------------------------------------------------------- /Anchors/Slides/5. Using Multiline Flag.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Anchors/Slides/5. Using Multiline Flag.pdf -------------------------------------------------------------------------------- /Characters/Slides/11. Unicode Matching.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/11. Unicode Matching.pdf -------------------------------------------------------------------------------- /Characters/Slides/4. Exploring The Api.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/4. Exploring The Api.pdf -------------------------------------------------------------------------------- /Characters/Slides/9. Metacharacters Pipe.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/9. Metacharacters Pipe.pdf -------------------------------------------------------------------------------- /Recipes/Slides/5. Matching Number Ranges.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Recipes/Slides/5. Matching Number Ranges.pdf -------------------------------------------------------------------------------- /Groups/Slides/8. Special Groups Lookahead.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Groups/Slides/8. Special Groups Lookahead.pdf -------------------------------------------------------------------------------- /Groups/Slides/9. Special Groups Lookbehind.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Groups/Slides/9. Special Groups Lookbehind.pdf -------------------------------------------------------------------------------- /Recipes/Slides/6. Matching Ipv4 Addresses.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Recipes/Slides/6. Matching Ipv4 Addresses.pdf -------------------------------------------------------------------------------- /Anchors/Slides/4. Implementing Dotall In Js.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Anchors/Slides/4. Implementing Dotall In Js.pdf -------------------------------------------------------------------------------- /Characters/Slides/10. RegExp Or Regex Literal.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/10. RegExp Or Regex Literal.pdf -------------------------------------------------------------------------------- /Characters/Slides/8. Selecting White Spaces.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/8. Selecting White Spaces.pdf -------------------------------------------------------------------------------- /Groups/Slides/4. Backreference & Replace Method.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Groups/Slides/4. Backreference & Replace Method.pdf -------------------------------------------------------------------------------- /Recipes/Slides/2. Applying Syntax Highlight #01.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Recipes/Slides/2. Applying Syntax Highlight #01.pdf -------------------------------------------------------------------------------- /Groups/Slides/3. Capturing & Non-capturing Group.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Groups/Slides/3. Capturing & Non-capturing Group.pdf -------------------------------------------------------------------------------- /Quantifiers/Slides/3. Quantifiers Zero Or One Of.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Quantifiers/Slides/3. Quantifiers Zero Or One Of.pdf -------------------------------------------------------------------------------- /Quantifiers/Slides/4. Quantifiers One Or More Of.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Quantifiers/Slides/4. Quantifiers One Or More Of.pdf -------------------------------------------------------------------------------- /Quantifiers/Slides/5. Quantifiers Zero Or More Of.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Quantifiers/Slides/5. Quantifiers Zero Or More Of.pdf -------------------------------------------------------------------------------- /Groups/NestedGroups.js: -------------------------------------------------------------------------------- 1 | const sentence = ` 2 | SuperSonic 3 | HyperSonic 4 | UltraSonic 5 | ` 6 | 7 | console.log(sentence.match(/(?
(?Su|Hy|Ul)per|Ultra)Sonic/));


--------------------------------------------------------------------------------
/Quantifiers/Slides/11. Challenge 3# Matching E-mail.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Quantifiers/Slides/11. Challenge 3# Matching E-mail.pdf


--------------------------------------------------------------------------------
/CharacterClasses/Slides/6. Shorthand Character Classes.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/CharacterClasses/Slides/6. Shorthand Character Classes.pdf


--------------------------------------------------------------------------------
/Characters/AnyWhiteSpace.js:
--------------------------------------------------------------------------------
1 | const userData = `{
2 |     "name": "John",
3 |     "age": 43,
4 |     "email": "john@smith.com"
5 | }`
6 | console.log(userData.match(/\s\s/g));	  


--------------------------------------------------------------------------------
/CharacterClasses/Slides/2. Working With Character Classes.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/CharacterClasses/Slides/2. Working With Character Classes.pdf


--------------------------------------------------------------------------------
/Characters/Slides/7. Metacharacters Any Single Character.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Characters/Slides/7. Metacharacters Any Single Character.pdf


--------------------------------------------------------------------------------
/Quantifiers/Slides/10. Challenge 2# Matching Phone Number.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Quantifiers/Slides/10. Challenge 2# Matching Phone Number.pdf


--------------------------------------------------------------------------------
/Quantifiers/Slides/6. Quantifier {n, M} (matches Exactly N).pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Quantifiers/Slides/6. Quantifier {n, M} (matches Exactly N).pdf


--------------------------------------------------------------------------------
/CharacterClasses/Slides/7. Negated Shorthand Character Classes.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/CharacterClasses/Slides/7. Negated Shorthand Character Classes.pdf


--------------------------------------------------------------------------------
/CharacterClasses/Slides/4. Character Classes And Metacharacters.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/CharacterClasses/Slides/4. Character Classes And Metacharacters.pdf


--------------------------------------------------------------------------------
/Quantifiers/Slides/9. Challenge 1#  Matching Social Security Number.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/cod3rcursos/regex-course/HEAD/Quantifiers/Slides/9. Challenge 1#  Matching Social Security Number.pdf


--------------------------------------------------------------------------------
/CharacterClasses/MetacharactersAndClasses.js:
--------------------------------------------------------------------------------
1 | const phoneNumber = "[Joshua] +1 (613) 555-0189"
2 | const metacharacters = /[()]+]/g
3 | const result = phoneNumber.match(metacharacters)
4 | console.log(result);
5 | 


--------------------------------------------------------------------------------
/Characters/UnicodeMatching.js:
--------------------------------------------------------------------------------
1 | const sentence = "Here are some cool looking characters & emojis Π✅⌚⛄"
2 | const unicodes = /\u2705|\u231A|\u26C4|\u03A0/g
3 | const result = sentence.match(unicodes)
4 | console.log(result);


--------------------------------------------------------------------------------
/CharacterClasses/UnicodeRange.js:
--------------------------------------------------------------------------------
1 | const mathExp = "∀x∀y[∀z(z∈x↔z∈y)→x=y]"
2 | const regex = /[∀-⋿←-⇿]/g
3 | const regex2 = /[\u{2200}-\u{22FF}\u{2190}-\u{21FF}]/gu
4 | 
5 | console.log(mathExp.match(regex));
6 | console.log(mathExp.match(regex2));


--------------------------------------------------------------------------------
/Recipes/zip-code/ZipCode.js:
--------------------------------------------------------------------------------
 1 | const input = `
 2 | 12345-6789
 3 | 12345
 4 | 12345-
 5 | 123456789
 6 | 12345678910
 7 | 123456789-
 8 | `
 9 | 
10 | // Expected output: [ '12345-6789', '12345' ]
11 | console.log(input.match(/^[0-9]{5}(?:-[0-9]{4})?$/gm));


--------------------------------------------------------------------------------
/Recipes/NumberRanges/NumberRanges.js:
--------------------------------------------------------------------------------
 1 | const numbers = 
 2 | `1
 3 | 50
 4 | 99
 5 | 100
 6 | 150
 7 | 179
 8 | 180
 9 | 185
10 | 187
11 | 189`
12 | 
13 | const matchNumbers = /^(?:[0-9]{1,2}|1[0-7][0-9]|18[0-7])$/gm
14 | 
15 | console.log(numbers.match(matchNumbers));


--------------------------------------------------------------------------------
/Characters/RegexpOrRegexLiteral.js:
--------------------------------------------------------------------------------
1 | 
2 | const literal = /a\|b/;
3 | const exp = new RegExp("a\\|b")
4 | 
5 | const sentence = 'The alternation operator is represented by the pipe operator("a|b")';
6 | 
7 | console.log(sentence.match(literal));
8 | console.log(sentence.match(exp));


--------------------------------------------------------------------------------
/Groups/NamedCapturingGroups.js:
--------------------------------------------------------------------------------
1 | var sentence = `
2 | — My name is Bond, James Bond James.
3 | — You can call me English, Johnny English...
4 | — And I'm Bernard, Andrew Baines Bernard`;
5 | 
6 | console.log(sentence.match(/(?\w+), (?\w+) \k/gi));
7 | 


--------------------------------------------------------------------------------
/Quantifiers/OneOrMoreOf.js:
--------------------------------------------------------------------------------
1 | const files = ["style.css", "theme.scss", "User.js", "Login.jsx", "LoginRefactor.tsx", "UserModel.ts"]
2 | const sentence = files.join("\n")
3 | console.log(sentence);
4 | // [1-9]+
5 | // \w+
6 | console.log(sentence.match(/\w+\.(json|s?css|jsx?|tsx?)/g));


--------------------------------------------------------------------------------
/Groups/CapturingAndNonCapturing.js:
--------------------------------------------------------------------------------
1 | var sentence = `
2 | — My name is Bond, James Bond James.
3 | — You can call me English, Johnny English...
4 | — And I'm Bernard, Andrew Baines Bernard`;
5 | 
6 | console.log(sentence.match(/(\w+), (\w+) \1/gi));
7 | console.log(sentence.match(/(?:\w+), (\w+) \1/gi));


--------------------------------------------------------------------------------
/Characters/Metacharacters.js:
--------------------------------------------------------------------------------
1 | /*
2 |     A metacharacter is a character that has a
3 |     special meaning during pattern processing. 
4 |     You use metacharacters in regular expressions
5 |     to define the search criteria and any text 
6 |     manipulations.
7 |     
8 |     — IBM Knowledge Center
9 | */


--------------------------------------------------------------------------------
/Anchors/WordBondaries.js:
--------------------------------------------------------------------------------
 1 | const sentences = [
 2 |     'Calm',
 3 |     'Becalmed',
 4 |     'Calmer',
 5 |     'Super-Calm'
 6 | ]
 7 | 
 8 | const validAssignment = /^(let|var|const) \w+ = (\d+|"\w*");$/
 9 | 
10 | for (const sentence of sentences) {
11 |     console.log(validAssignment.test(sentence)); 
12 | }


--------------------------------------------------------------------------------
/Groups/Lookbehind.js:
--------------------------------------------------------------------------------
 1 | const sentence = `
 2 | Mr. Brown
 3 | Mr. Blue
 4 | Mr. Blonde
 5 | Mr. White
 6 | Mr. Pink
 7 | Mr. Orange
 8 | Nice Guy Eddie
 9 | `
10 | 
11 | console.log(sentence.match(/(?<=Mr\. )\w+/g));
12 | console.log(sentence.match(/(?\d+#) (?\w+) (?\d+)$/gm
 7 | 
 8 | let matchData
 9 | 
10 | while(matchData = scoreData.exec(sentence)) {
11 |     const {pos, name, points} = matchData.groups
12 |     console.log(`Name: ${name}\nPosition: ${pos}\nPoints: ${points}`);
13 |     console.log("---");
14 |     
15 | }
16 | 


--------------------------------------------------------------------------------
/Characters/HelloRegex.js:
--------------------------------------------------------------------------------
 1 | const sentence  = "I Scream, You Scream, We All Scream for Ice Cream"
 2 | // In JavaScript, regular expressions are Objects!
 3 | const regexpInstance = new RegExp(/You/)
 4 | const regexLiteral = /Scream/
 5 | // const regexpInstance = new RegExp(regexLiteral)
 6 | 
 7 | const result = regexpInstance.exec(sentence)
 8 | console.log(sentence.match(regexpInstance))
 9 | console.log(sentence.match(regexLiteral))
10 | 


--------------------------------------------------------------------------------
/Characters/AnySingleCharacter.js:
--------------------------------------------------------------------------------
 1 | const phoneNumber1 = "(222) 555-1234"
 2 | const phoneNumber2 = "(333) 555-1234"
 3 | const phoneNumber3 = "(444) 555-1234"
 4 | const areaCode = /\(222\)/ 
 5 | 
 6 | console.log(phoneNumber1.match(areaCode));
 7 | console.log(phoneNumber2.match(areaCode));
 8 | console.log(phoneNumber3.match(areaCode));
 9 | 
10 | const symbols = "1,(#"
11 | const anySingle = /.{4}/ 
12 | 
13 | 
14 | console.log(symbols.match(anySingle));


--------------------------------------------------------------------------------
/CharacterClasses/Ranges.js:
--------------------------------------------------------------------------------
1 | const addressInfo = "116 Winners Cir Hessmer, Louisiana(LA), 71341"
2 | const numbersOnly = /[0-9]/g // at the end Tweak range
3 | const capitalOnly = /[A-Z]/g
4 | const lowerOnly = /[a-z]/g
5 | const letters = /[B-Q1-6]/g // at the end Tweak mixed range 
6 | console.log(addressInfo.match(numbersOnly));
7 | console.log(addressInfo.match(capitalOnly));
8 | console.log(addressInfo.match(lowerOnly));
9 | console.log(addressInfo.match(letters));


--------------------------------------------------------------------------------
/CharacterClasses/CharacterClasses.js:
--------------------------------------------------------------------------------
 1 | const addressInfo = "116 Winners Cir Hessmer, Louisiana(LA), 71341"
 2 | // const numbersOnly = /0|1|2|3|4|5|6|7|8|9/g
 3 | const numbersOnly = /[0123456789]/g
 4 | const oddOnly = /[13579]/g
 5 | const evenOnly = /[24680]/g
 6 | const vowels = /[aeiou]/g
 7 | console.log(addressInfo.match(numbersOnly));
 8 | console.log(addressInfo.match(oddOnly));
 9 | console.log(addressInfo.match(evenOnly));
10 | console.log(addressInfo.match(vowels));


--------------------------------------------------------------------------------
/Characters/Flags.js:
--------------------------------------------------------------------------------
 1 | /*
 2 |     Flags are optional Meta Characters that can change the
 3 |     search behaviour of a regular expression.
 4 |     g - Global
 5 |     i - Ignore Case
 6 | */
 7 |  
 8 | const pattern = new RegExp(/,/, "g")
 9 | const commaMatch = sentence.match(/,/g)
10 | const screamMatch = sentence.match(/Scream/g)
11 | const creamMatch = sentence.match(/cream/gi)
12 | console.log(commaMatch);
13 | console.log(screamMatch);
14 | console.log(creamMatch);
15 | 


--------------------------------------------------------------------------------
/Quantifiers/Emails.js:
--------------------------------------------------------------------------------
 1 | const input = `
 2 | afidge_0@friendfeed.us
 3 | cmacgauhy.1@bloomberg.org
 4 | rhaseley2@ow.ly
 5 | i_billiard4@sohu.@
 6 | fbrandel3@gmail.com
 7 | rgoldring6@timesonline.
 8 | `
 9 | 
10 | /*
11 | *   expected output:
12 | *   [
13 | *       'afidge_0@friendfeed.us',
14 | *       'cmacgauhy.1@bloomberg.org',
15 | *       'rhaseley2@ow.ly',
16 | *       'fbrandel3@gmail.com'
17 | *   ]
18 | */
19 | 
20 | // Write your code here...
21 | console.log(input.match(/[\w.]+@\w+\.\w{2,4}[a-z.]{0,3}/g));


--------------------------------------------------------------------------------
/Characters/SimpleCharacters.js:
--------------------------------------------------------------------------------
 1 | const fs = require("fs");
 2 | const path = require("path");
 3 | 
 4 | const userDataPath = path.join(__dirname, "data", "users.csv");
 5 | const users = fs.readFileSync(userDataPath).toString();
 6 | 
 7 | const commaSeparator = /,/
 8 | console.log(users.split(commaSeparator))
 9 | console.log(users.match(/,/g))
10 | console.log(users.match(/Bailes/))
11 | console.log(users.match(/Bailes/gi))
12 | console.log(users.match(/4/gi))
13 | 
14 | // How can we separate the rows? The answer? Meta-Characters!


--------------------------------------------------------------------------------
/Groups/WorkingWithGroups.js:
--------------------------------------------------------------------------------
 1 | const sentence = `
 2 | Attention! This is a top-level secret!
 3 | Attention! This is a mid-level secret!
 4 | Meh... This is a bottom-level secret...
 5 | `
 6 | 
 7 | // console.log(sentence.match(/[a-zA-z0-9_.]+@\w+\.\w{2,4}(\.\w{2,3})?/g));
 8 | console.log(sentence.match(/\w{3,6}-level/g));
 9 | console.log(sentence.match(/(top|mid|bottom)-level/g));
10 | 
11 | const urls = `
12 | www.amazon.com
13 | gmail.com
14 | www.reddit.com
15 | `
16 | 
17 | console.log(urls.match(/(w{3}\.)?\w+\.\w{2,3}/g));
18 | 
19 | 
20 | const emailRegexRefactor = /[\w\.]+@\w+\.\w{2,4}(\.\w{2})?/g


--------------------------------------------------------------------------------
/Recipes/syntax-highlight/utils/files.js:
--------------------------------------------------------------------------------
 1 | const fs = require('fs')
 2 | const path = require('path')
 3 | const rootDirPath = path.dirname(__dirname)
 4 | 
 5 | const read = fileName => {
 6 |     const filePath = path.join(rootDirPath, "src", fileName)
 7 |     return fs.readFileSync(filePath, { encoding: 'utf8' })
 8 | }
 9 | 
10 | 
11 | const write = (fileName, content) => {
12 |     const dirname = path.join(rootDirPath, "modified")
13 |     if (!fs.existsSync(dirname)) {
14 |         fs.mkdirSync(dirname)
15 |     }
16 | 
17 |     fs.writeFileSync(`${dirname}/${fileName}`, content, { encoding: 'utf8' })
18 | }
19 | 
20 | module.exports = { read, write }


--------------------------------------------------------------------------------
/CharacterClasses/NegatedCharacterClasses.js:
--------------------------------------------------------------------------------
 1 | const addressInfo = `
 2 |     +1 (408) 996-1010
 3 |     One Apple Park Way Cupertino, CA 95014 United States
 4 | `
 5 | const flightId = "4815162342";
 6 | console.log(flightId.match(/[^02468]/g))
 7 | console.log(flightId.match(/[^2-4]/g))
 8 | 
 9 | console.log(addressInfo.match(/\D/g));
10 | console.log(addressInfo.match(/[^0-9]/g));
11 | 
12 | console.log("**Any non-whitespace**");
13 | console.log(addressInfo.match(/\S/g));
14 | console.log(addressInfo.match(/[^\n\r\t\f ]/g));
15 | 
16 | console.log("**Any non-word character**");
17 | console.log(addressInfo.match(/\W/g));
18 | console.log(addressInfo.match(/[^a-zA-Z0-9_]/g));


--------------------------------------------------------------------------------
/Characters/AlternationOperator.js:
--------------------------------------------------------------------------------
 1 | const message = "1 or 2? Vote now on your phones!";
 2 | const votes = "John voted: 2, Mike voted: 1, Kate voted: 1, James voted: 0";
 3 | // console.log(votes.match(/or|te/));
 4 | 
 5 | const question = "Do you have a drivers license?"
 6 | const answer = "yup";
 7 | const validAnswers = /yes|Yes|no|No/;
 8 | console.log(validAnswers.test(answer));
 9 | console.log(answer.match(validAnswers));
10 | 
11 | // Introduction
12 | // In this lesson i'd like to introduce you to the alternation operator.
13 | // Build Case
14 | // Introduce the pipe operator(without, then with the global flag)
15 | // Exercise
16 | // Given this results string, how Would you extract the only the results?
17 | // Or, we could use the pipe operator.
18 | 
19 | 


--------------------------------------------------------------------------------
/Characters/MatchingCharacters.js:
--------------------------------------------------------------------------------
 1 | /*
 2 | - User Tag anatomy:
 3 | - Starts with an @ sign
 4 | - Uses letters to define the user tag
 5 | - Ends with a pound sign and the user id
 6 | 
 7 | Example: 
 8 |     @userTag#5213
 9 | */ 
10 | const userTagInput = "@userTag#5213";
11 | 
12 | let valid = false
13 | const poundCharacterIndex = userTagInput.length - 5
14 | const userId = userTagInput.substring(poundCharacterIndex + 1, userTagInput.length)
15 | 
16 | const doesntContainWhiteSpaces = userTagInput.indexOf(' ') == -1
17 | const startsWithAt = userTagInput[0] === '@'
18 | const hasPoundSeparator = userTagInput[poundCharacterIndex] === '#'
19 | const idMadeOfNumbers = !isNaN(userId)
20 | 
21 | valid = 
22 |     doesntContainWhiteSpaces &&
23 |     startsWithAt && 
24 |     hasPoundSeparator && 
25 |     idMadeOfNumbers
26 | 
27 | 
28 | console.log(valid);


--------------------------------------------------------------------------------
/Recipes/syntax-highlight/utils/Highlighter.js:
--------------------------------------------------------------------------------
 1 | class Highlighter {
 2 |     constructor(sourceCode) {
 3 |         this._original = sourceCode
 4 |         this._modified = sourceCode
 5 |     }
 6 |     /**
 7 |      * Matches and applies syntax highlighting to desired language token or tokens.
 8 |      * @param {RegExp} tokenPattern - Search pattern to match a desired language token or tokens.
 9 |      * @param {string} color - Color that will be applied to the matched token or tokens.
10 |      * @returns {Object} Highlighter instance
11 |      */
12 |     setColor(tokenPattern, color) {
13 |         this._modified = this._modified.replace(tokenPattern, `$1`)
14 |         return this
15 |     }
16 | 
17 |     get original() {
18 |         return this._original
19 |     }
20 | 
21 |     get styledCode() {
22 |         return this._modified
23 |     }
24 | }
25 | 
26 | module.exports = Highlighter;


--------------------------------------------------------------------------------
/Recipes/syntax-highlight/src/sourceCode.html:
--------------------------------------------------------------------------------
 1 | 
 2 | 
 3 | 
 4 | 
 5 |     
 6 |     
 7 |     
 8 |     Source Code
 9 |     
14 | 
15 | 
16 | 
17 |     

Source Code

18 |
19 |         
20 | package cod3r;
21 | 
22 | /*
23 |  * Print Student's Grade
24 |  */
25 | public class Grade {
26 | 
27 |     // Entry Point
28 | 
29 |     public static void main(String[] args) {
30 |         int grade = 7;
31 | 
32 |         if(grade >= 7) {
33 |             System.out.println("Approved");
34 |         } else {
35 |             System.out.println("Failed");
36 |         }
37 |     }
38 | }
39 |         
40 |     
41 | 42 | 43 | -------------------------------------------------------------------------------- /Recipes/syntax-highlight/SyntaxHighlight.js: -------------------------------------------------------------------------------- 1 | const files = require('./utils/files') 2 | const Highlighter = require('./utils/Highlighter') 3 | 4 | const rawSourceCode = files.read('sourceCode.html') 5 | const matchCodeTagContentPattern = /[\s\S]*<\/code>/i 6 | let codeContent = rawSourceCode.match(matchCodeTagContentPattern)[0] 7 | 8 | const highligter = new Highlighter(codeContent); 9 | const stringPattern = /(".*")/g 10 | const keywordPattern = /\b(package|public|class|static|if|else)\b/g 11 | const typesPattern = /\b(void|int)\b/g 12 | const multilinePattern = /(\/\*[\s\S]*\*\/)/g 13 | const singlelinePattern = /(\/\/.*)/g 14 | // Write your code here... 15 | highligter 16 | .setColor(stringPattern, 'ce9178') // Strings 17 | .setColor(keywordPattern, 'd857cf') // Keywords 18 | .setColor(typesPattern, '1385e2') // Types 19 | .setColor(multilinePattern, '267703') // Multi-line Comments 20 | .setColor(singlelinePattern, '267703') // Single-line Comments 21 | 22 | const styledSourceCode = rawSourceCode.replace(matchCodeTagContentPattern, highligter.styledCode) 23 | files.write('styledSourceCode.html', styledSourceCode) -------------------------------------------------------------------------------- /Characters/ExploringTheAPI.js: -------------------------------------------------------------------------------- 1 | const sentence = "I Scream, You Scream, We All Scream for Ice Cream" 2 | console.log(sentence.replace(/[A-Z]/g, ";")) 3 | console.log(sentence.split(/cream/gi)); 4 | sentence.match(/,/g) // => ["," , ","] 5 | sentence.match(/,/) 6 | /* => 7 | "[ 8 | ',', 9 | index: 8, 10 | input: 'I Scream, You Scream, We All Scream for Ice Cream', 11 | groups: undefined 12 | ]" 13 | */ 14 | sentence.match(/popsicles/g) // => null 15 | 16 | console.log(sentence.split(" ")); 17 | sentence.split(/,/) 18 | console.log(sentence.split(/cream/g)); // => not mutch difference use limit instead 19 | sentence.split(/cream/i) // => more flexible 20 | 21 | sentence.replace(",", "#") // => I Scream# You Scream, We All Scream for Ice Cream 22 | 23 | 24 | sentence.replace(/,/g, "/") 25 | // sentence.replace(/,/g, "\") 26 | 27 | const matchComma = sentence.match(/,/g) 28 | const splitByComma = sentence.split(/,/g) 29 | const replaceComma = sentence.replace(/,/g, "/") 30 | // const replaceComma = sentence.replace(/,/g, "\"") 31 | console.log(matchComma); 32 | console.log(splitByComma); 33 | console.log(replaceComma); 34 | // console.log(newSentence); 35 | -------------------------------------------------------------------------------- /Characters/EscapeSequences.js: -------------------------------------------------------------------------------- 1 | /* 2 | Escape sequences are typically used to specify actions 3 | such as carriage returns and tab movements on terminals 4 | and printers. They are also used to provide literal 5 | representations of nonprinting characters and characters 6 | that usually have special meanings, such as the double 7 | quotation mark ("). 8 | — Microsoft Docs 9 | 10 | JS Special Characters 11 | ' - Single Quotation Mark 12 | " - Double Quotation Mark 13 | ` - Backtick 14 | \ - Backslash 15 | Useful Links: 16 | JavaScript Escape Sequences: https://www.w3schools.com/js/js_strings.asp 17 | Line Feed Vs Carriage Return: https://stackoverflow.com/a/1761086 18 | */ 19 | console.log('Hello \'World!\'') 20 | console.log("Hello \"World!\"") 21 | console.log(`Hello \`World!\``) 22 | const singleQuote = 'Hello \n World!' 23 | const doubleQuote = "Hello \t World!" 24 | const backtick = `Hello \r World!` 25 | const backslash = `Hello \\ World!` 26 | 27 | console.log(singleQuote) 28 | console.log(doubleQuote) 29 | console.log(backtick) 30 | console.log(backslash) 31 | 32 | const path = require("path"); -------------------------------------------------------------------------------- /Recipes/syntax-highlight/modified/styledSourceCode.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | Source Code 9 | 14 | 15 | 16 | 17 |

Source Code

18 |
19 |         
20 | package cod3r;
21 | 
22 | /*
23 |  * Print Student's Grade
24 |  */
25 | public class Grade {
26 | 
27 |     // Entry Point
28 | 
29 |     public static void main(String[] args) {
30 |         int grade = 7;
31 | 
32 |         if(grade >= 7) {
33 |             System.out.println("Approved");
34 |         } else {
35 |             System.out.println("Failed");
36 |         }
37 |     }
38 | }
39 |         
40 |     
41 | 42 | 43 | -------------------------------------------------------------------------------- /Bonus/Cheatsheet.md: -------------------------------------------------------------------------------- 1 | # Regex Cheatsheet 2 | 3 | Hello, everyone! In this markdown file, we'll be covering the usage of regular expression in a few other languages by showing you each language specific syntax, and some Useful Regex Supporting API methods. Feel free to go throught the whole file or use the navigation index bellow. 4 | 5 | 1. [JavaScript](#javaScript) 6 | 2. [Go](#go) 7 | 3. [Java](#java) 8 | 4. [Python](#python) 9 | 5. [Ruby](#ruby) 10 | 6. [Additional Resources](#aditional-material) 11 | 12 | --- 13 | 14 | ## JavaScript 15 | 16 | ### Pattern Declaration 17 | 18 | In JavaScript, you can define regex patterns using **single-, double-quoted, or template strings**. An alternative to strings is **RegExp instances**, that be declared using the **RegExp Constructor** or the **literal notation**(double forwardslash). 19 | 20 | ```js 21 | const sentence = "The quick brown fox jumped over the lazy dog" 22 | 23 | // Regex Literal 24 | const thePattern = /the/ 25 | 26 | // RegExp Instance 27 | const thePattern1 = new RegExp("the") 28 | const thePattern2 = new RegExp(thePattern) 29 | ``` 30 | 31 | ### **Useful Regex Supporting API methods** 32 | 33 | #### `String.match(pattern):` 34 | 35 | It Tries to match the pattern on the target string. This method returns **null** if none was found or an array. If you are applying the global flag to the expression, the content of the array will be all the caputered occurences; if not, the array will contain a single match along with aditional informations about the captured value, such as its index, groups, and the targeted string. 36 | 37 | ```js 38 | const sentence = "The quick brown fox jumped over the lazy dog" 39 | const pattern = /the/ 40 | console.log(sentence.match(pattern)); 41 | ``` 42 | 43 | #### `String.split(pattern):` 44 | 45 | This method splits the string and returns an array containing the splitted values. The separator parameter determines the positions where string will be splitted. This parameter can be either a string, or a regular expression. On the exaple bellow, we're separating the string on each vowel. 46 | 47 | > **👀 Observation** 48 | > 49 | > Note that the splitted string array **does not** include the separators. 50 | 51 | ```js 52 | const sentence = "The quick brown fox jumped over the lazy dog" 53 | const separatorPattern = /[aeiou]/ 54 | console.log(sentence.split(separatorPattern)); 55 | ``` 56 | 57 | #### `String.replace(pattern, replaceValue):` 58 | 59 | This method replaces a value on the string with another, it can be a character, a word or a full sentence. The first parameter(searchValue) can be either a string, or a regular expression which will search for the value or values that will be replaced; the second paramenter(replaceValue) is the value that will replace captured value. 60 | 61 | ```js 62 | const sentence = "The quick brown fox jumped over the lazy dog" 63 | const searchPattern = /o/ 64 | console.log(sentence.replace(searchPattern, "i")); 65 | ``` 66 | 67 | #### `RegExp.test(string):` 68 | 69 | This method checks if the given string can be matched by the target regular expression and returns a boolean. 70 | 71 | ```js 72 | const sentence = "The quick brown fox jumped over the lazy dog" 73 | const pattern = /quick/ 74 | console.log(pattern.test(sentence)) 75 | ``` 76 | 77 | #### `RegExp.exec(string):` 78 | This method works similarly to the match method, but with a few key differences. 79 | 80 | 1. It only returns only one match, **regardless** of the presence of the global flag. 81 | 2. Modifies some properties on the RegExp Instance after the match. If you are interested in knowing which values are modified, here's the [documentation link](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp/exec#description) for reference. Take a look at the Description section. 82 | 83 | 84 | ```js 85 | const sentence = "The quick brown fox jumped over the lazy dog" 86 | const pattern = /o/ 87 | const pattern2 = /o/g 88 | 89 | // Both produce the same output 90 | console.log(pattern.exec(sentence)) 91 | console.log(pattern2.exec(sentence)) 92 | ``` 93 | 94 | --- 95 | ## **Go** 96 | 97 | ### Pattern Declaration 98 | 99 | #### **Strings** 100 | 101 | Regex patterns in Go can be defined with strings. You can either use regular double-quoted strings(**requires double escaping** just like in JavaScript); or literal strings which are declared with backticks, that (**does not require** double escaping). 102 | 103 | ```go 104 | package main 105 | 106 | import (**** 107 | "regexp" 108 | ) 109 | 110 | func main() { 111 | sentence := "The quick brown fox jumped over the lazy dog" 112 | thePattern := `the` 113 | theSecondPattern := "the" 114 | } 115 | ``` 116 | 117 | #### **Compile & MustCompile** 118 | 119 | An alternative to Strings is the **Compile** and **MustCompile** methods. Both expect a double-quoted or literal String pattern, parses it to a RegExp instance, which can then be used against text. 120 | 121 | > **📘 Compile Vs MustCompile** 122 | > 123 | > There's a slight difference between these two methods. **Compile** returns two values, a regexp instance and an error object; while the **MustCompile** returns only the regexp instance, but panics if something happens in the parsing process. 124 | 125 | ```go 126 | package main 127 | 128 | import ( 129 | "regexp" 130 | ) 131 | 132 | func main() { 133 | sentence := "The quick brown fox jumped over the lazy dog" 134 | pattern := `the` 135 | 136 | cRegexpInstance, err := regexp.Compile(pattern) 137 | mcRegexpInstance2 := regexp.MustCompile(pattern) 138 | } 139 | ``` 140 | 141 | ### **Useful Regex Supporting API methods** 142 | 143 | In my opinion, Golang has a really good documentation. There, you will not only find the methods' signatures but also a well written description along with a simple example. With that said, there's not much I have to add in this section of our file besides sharing the link for the [**Original RegExp Docs**](https://golang.org/pkg/regexp/) and my strong recomendations to take a look at it. 144 | 145 | --- 146 | 147 | ## **Java** 148 | 149 | [Java's Official Documentation](https://docs.oracle.com/javase/7/docs/api/java/util/regex/Pattern.html) offers an overview on the comprising parts of the **Regex Package**, along with its supporting flags and metacharacters, and each methods' signatures paired with a concise definition, but unfortunately, it lacks on simple examples. In this section, we'll be targeting that. 150 | 151 | ### Pattern Declaration 152 | 153 | Pattern declaration in Java is made with the `Pattern.compile()` method, which expects a **String** as the pattern parameter. 154 | 155 | > **👀 Observation** 156 | > 157 | > Java **does not** have a similar solution to **JavaScript's Template String or Golang's Literal String**, so **we must always double escape some metacharacters(e.g shorthands)**. 158 | 159 | ```java 160 | import java.util.regex.*; 161 | 162 | class teste { 163 | public static void main(String args[]) { 164 | String sentence = "The quick brown fox jumped over the lazy dog"; 165 | Pattern pattern = Pattern.compile("the"); 166 | } 167 | } 168 | ``` 169 | 170 | ### **Useful Regex Supporting API methods** 171 | 172 | #### compile(String regex, int flags?) 173 | Compiles the given regular expression into a pattern with the given flags. 174 | 175 | This method has two parameters: 176 | 1. `String regex`: The expression to be compiled 177 | 2. `int flags` - The flags that will be applied to the pattern. In Java, the flags are represented as **bitmasks**. For more information on which flags Java Supports, they are listed and described at the [official documentation](https://docs.oracle.com/javase/7/docs/api/java/util/regex/Pattern.html) 178 | 179 | This method returns a `Pattern` instance. 180 | 181 | 182 | ```java 183 | import java.util.regex.*; 184 | 185 | class teste { 186 | public static void main(String args[]) { 187 | String sentence = "The quick brown fox jumped over the lazy dog"; 188 | Pattern pattern = Pattern.compile("the"); 189 | } 190 | } 191 | ``` 192 | 193 | #### `Pattern.matcher(String regex, int flags?)` 194 | 195 | Creates a `Matcher` that will match the given input against this pattern. 196 | 197 | This method returns a new `Matcher` for this pattern. 198 | 199 | #### `Matcher.matches(String regex, int flags?)` 200 | 201 | Compiles the given regular expression and attempts to match the given input against it. 202 | 203 | This method returns a `boolean`; `true` if, and only if, a subsequence of the input sequence matches this matcher's pattern. 204 | 205 | 206 | #### `String.split(String regex, int flags?)` 207 | 208 | Splits the given input sequence around matches of this pattern. 209 | 210 | This method returns the `Array` of `Strings` computed by splitting the input around matches of this pattern. 211 | 212 | 213 | #### `find(String regex, int flags?)` 214 | 215 | Attempts to find the next subsequence of the input sequence that matches the pattern. 216 | 217 | This method returns a `boolean`; `true` if, and only if, a subsequence of the input sequence starting at the given index matches this matcher's pattern. 218 | 219 | #### `group(String regex, int flags?)` 220 | 221 | Returns the input subsequence matched by the previous match. 222 | 223 | This method returns a `String`; The (possibly empty) subsequence captured by the group during the previous match, or null if the group failed to match part of the input. 224 | 225 | --- 226 | 227 | ## Python 228 | 229 | ### Pattern Declaration 230 | 231 | ### **Useful Regex Supporting API methods** 232 | 233 | 234 | --- 235 | ## Ruby 236 | 237 | ### Pattern Declaration 238 | 239 | ### **Useful Regex Supporting API methods** 240 | 241 | 242 | ## **Additional Resources** 243 | 244 | ### Reading Material 245 | 246 | - [Rexegg](http://www.rexegg.com/) 247 | - [regular-expressions.info](https://www.regular-expressions.info/javascript.html) 248 | - [javascript.info](https://javascript.info/regular-expressions) 249 | - Mastering Regular Expressions(book) 250 | - Regular Expressions Cookbook(book) 251 | 252 | ### Testing, Debugging & Visualizing 253 | - [Regex101](https://regex101.com/) 254 | - [Regexr](https://regexr.com/) 255 | - [Regexper](https://regexper.com/) -------------------------------------------------------------------------------- /Cheatsheet.md: -------------------------------------------------------------------------------- 1 | # Regex Cheatsheet 2 | 3 | Hello, everyone! In this markdown file, we'll be covering the usage of regular expressions in a few other languages by showing you each language specific syntax, and some Useful Regex Supporting API methods. Feel free to go through the whole file or use the navigation index below. 4 | 5 | 1. [JavaScript](#javaScript) 6 | 2. [Go](#go) 7 | 3. [Java](#java) 8 | 4. [Python](#python) 9 | 5. [Ruby](#ruby) 10 | 6. [Additional Resources](#additional-resources) 11 | 12 | --- 13 | 14 | ## JavaScript 15 | 16 | ### Pattern Declaration 17 | 18 | In JavaScript, you can define regex patterns using **single-, double-quoted, or template strings**. An alternative to strings is **RegExp instances**, that can be declared using the **RegExp Constructor** or the **literal notation**(double forward slash). 19 | 20 | ```js 21 | const sentence = "The quick brown fox jumped over the lazy dog" 22 | 23 | // Regex Literal 24 | const thePattern = /the/ 25 | 26 | // RegExp Instance 27 | const thePattern1 = new RegExp("the") 28 | const thePattern2 = new RegExp(thePattern) 29 | ``` 30 | 31 | ### **Useful Regex Supporting API methods** 32 | 33 | #### `String.match(pattern):` 34 | 35 | It Tries to match the pattern on the target string. This method returns **null** if none (or an array) is found. If you are applying the global flag to the expression, the content of the array will be all the captured occurrences; if not, the array will contain a single match along with additional information about the captured value, such as its index, groups, and the targeted string. 36 | 37 | ```js 38 | const sentence = "The quick brown fox jumped over the lazy dog" 39 | const pattern = /the/ 40 | console.log(sentence.match(pattern)); 41 | ``` 42 | 43 | #### `String.split(pattern):` 44 | 45 | This method splits the string and returns an array containing the splitted values. The separator parameter determines the positions where the string will be splitted. This parameter can be either a string, or a regular expression. On the example below, we're separating the string on each vowel. 46 | 47 | > **👀 Observation** 48 | > 49 | > Note that the splitted string array **does not** include the separators. 50 | 51 | ```js 52 | const sentence = "The quick brown fox jumped over the lazy dog" 53 | const separatorPattern = /[aeiou]/ 54 | console.log(sentence.split(separatorPattern)); 55 | ``` 56 | 57 | #### `String.replace(pattern, replaceValue):` 58 | 59 | This method replaces a value on the string with another; it can be a character, a word or a full sentence. The first parameter(searchValue) can be either a string or a regular expression, which will search for the value or values that will be replaced; the second parameter(replaceValue) is the value that will replace the captured value. 60 | 61 | ```js 62 | const sentence = "The quick brown fox jumped over the lazy dog" 63 | const searchPattern = /o/ 64 | console.log(sentence.replace(searchPattern, "i")); 65 | ``` 66 | 67 | #### `RegExp.test(string):` 68 | 69 | This method checks if the given string can be matched by the target regular expression and then returns a boolean. 70 | 71 | ```js 72 | const sentence = "The quick brown fox jumped over the lazy dog" 73 | const pattern = /quick/ 74 | console.log(pattern.test(sentence)) 75 | ``` 76 | 77 | #### `RegExp.exec(string):` 78 | 79 | This method works similarly to the match method, but with a few key differences. 80 | 81 | 1. It returns only one match, **regardless** of the presence of the global flag. 82 | 2. Modifies some properties on the RegExp Instance **after** the match. If you are interested in knowing which values are modified, here's the [documentation link](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp/exec#description) for reference. Take a look at the Description section. 83 | 84 | 85 | ```js 86 | const sentence = "The quick brown fox jumped over the lazy dog" 87 | const pattern = /o/ 88 | const pattern2 = /o/g 89 | 90 | // Both produce the same output 91 | console.log(pattern.exec(sentence)) 92 | console.log(pattern2.exec(sentence)) 93 | ``` 94 | 95 | --- 96 | ## **Go** 97 | 98 | ### Pattern Declaration 99 | 100 | #### **Strings** 101 | 102 | Regex patterns in Go can be defined with strings. You can either use regular double-quoted strings(**requires double escaping** just like in JavaScript) or literal strings, which are declared with backticks and **do not require** Double escaping. 103 | 104 | ```go 105 | package main 106 | 107 | import (**** 108 | "regexp" 109 | ) 110 | 111 | func main() { 112 | sentence := "The quick brown fox jumped over the lazy dog" 113 | thePattern := `the` 114 | theSecondPattern := "the" 115 | } 116 | ``` 117 | 118 | #### **Compile & MustCompile** 119 | 120 | Alternatives to **standalone** Strings are the **Compile** and **MustCompile** methods. Both expect a double-quoted or literal String pattern, parses it to a RegExp instance, which can then be used against text. 121 | 122 | > **📘 Compile Vs MustCompile** 123 | > 124 | > There's a slight difference between these two methods: **Compile** returns two values, a regexp instance and an error object, while the **MustCompile** returns only the regexp instance, but panics if something happens in the parsing process. 125 | 126 | ```go 127 | package main 128 | 129 | import ( 130 | "regexp" 131 | ) 132 | 133 | func main() { 134 | sentence := "The quick brown fox jumped over the lazy dog" 135 | pattern := `the` 136 | 137 | cRegexpInstance, err := regexp.Compile(pattern) 138 | mcRegexpInstance2 := regexp.MustCompile(pattern) 139 | } 140 | ``` 141 | 142 | ### **Useful Regex Supporting API methods** 143 | 144 | In my opinion, Golang has a really good documentation. In it, you will not only find the methods' signatures but also a well written description along with a simple example. Having said that, there's not much I have to add in this section of our file besides sharing the link for the [**Original RegExp Docs**](https://golang.org/pkg/regexp/) and strongly recommend that you take a look at it. 145 | 146 | --- 147 | 148 | ## **Java** 149 | 150 | [**Java's Official Documentation**](https://docs.oracle.com/javase/7/docs/api/java/util/regex/Pattern.html) offers an overview on the comprising parts of the **Regex Package**, along with its supporting flags and metacharacters, and each methods' signatures paired with a concise definition, but unfortunately, it is lacking on simple examples. In this section, we'll be targeting that. 151 | 152 | ### Pattern Declaration 153 | 154 | Pattern declaration in Java is made with the `Pattern.compile()` method, which expects a **String** as the pattern parameter. 155 | 156 | > **👀 Observation** 157 | > 158 | > Java **does not** have a similar solution to **JavaScript's Template String** or **Golang's Literal String**, so **we must always double escape some metacharacters(e.g shorthands)**. 159 | 160 | ```java 161 | import java.util.regex.*; 162 | 163 | class Regex { 164 | public static void main(String args[]) { 165 | String sentence = "The quick brown fox jumped over the lazy dog"; 166 | Pattern pattern = Pattern.compile("the"); 167 | } 168 | } 169 | ``` 170 | 171 | ### **Useful Regex Supporting API methods** 172 | 173 | #### compile(String regex, int flags?) 174 | 175 | Compiles the given regular expression into a pattern with the given flags. 176 | 177 | This method has two parameters: 178 | 179 | 1. `String regex`: The expression to be compiled 180 | 2. `int flags` : The flags that will be applied to the pattern. In Java, the flags are represented as **bitmasks**. For more information on which flags Java Supports, they are listed and described at the [official documentation](https://docs.oracle.com/javase/7/docs/api/java/util/regex/Pattern.html) 181 | 182 | This method returns a `Pattern` instance. 183 | 184 | 185 | ```java 186 | import java.util.regex.*; 187 | 188 | class Regex { 189 | public static void main(String args[]) { 190 | String sentence = "The quick brown fox jumped over the lazy dog"; 191 | Pattern pattern = Pattern.compile("the"); 192 | } 193 | } 194 | ``` 195 | 196 | #### `Pattern.matcher(CharSequence input)` 197 | 198 | Creates a `Matcher` that will match a given input against this pattern. 199 | 200 | This method has one parameter: 201 | 202 | 1. `CharSequence input`: The test string 203 | 204 | This method returns a new `Matcher` for this pattern. 205 | 206 | ```java 207 | import java.util.regex.*; 208 | 209 | public class Regex { 210 | 211 | public static void main(String args[]) { 212 | String ssn = "123-45-7890"; 213 | Pattern pattern = Pattern.compile("\\d{3}-\\d{2}-\\d{3,4}"); 214 | 215 | Matcher matcher = pattern.matcher(ssn); 216 | } 217 | } 218 | ``` 219 | 220 | #### `Matcher.matches(String regex, CharSequence input)` 221 | 222 | The `Matcher.matches()` is used to match the input sequence against the full text(beginning to end). 223 | More info on [JavaTPoint](https://www.javatpoint.com/post/java-matcher-matches-method) 224 | 225 | This method returns a `boolean` 226 | 227 | ```java 228 | import java.util.regex.*; 229 | 230 | class Regex { 231 | public static void main(String args[]) { 232 | String ssn = "123-45-7890"; 233 | Pattern pattern = Pattern.compile("\\d{3}-\\d{2}-\\d{3,4}"); 234 | 235 | Matcher matcher = pattern.matcher(ssn); 236 | System.out.println(matcher.matches()); // true 237 | } 238 | } 239 | ``` 240 | 241 | #### `String.split(CharSequence input, int limit)` 242 | 243 | Splits a given `String` into an `Array` of substrings, resulting in a new `Array`. 244 | 245 | ```java 246 | import java.util.regex.*; 247 | 248 | class Regex { 249 | public static void main(String args[]) { 250 | String html = "#001 Desmond#002 Jin#003 Kate#004 Locke"; 251 | String[] value = html.split("#\\d{3} "); 252 | for (String string : value) { 253 | System.out.println(string); 254 | } 255 | } 256 | } 257 | ``` 258 | 259 | #### `find(int start)` 260 | 261 | Searches for the next subsequence of the input that matches the pattern. 262 | 263 | Besides returning a `boolean`, this method also change the values on some properties on the previously initialized `Matcher` instance, such as: 264 | 265 | 1. `group` 266 | 2. `start` 267 | 3. `end` 268 | 269 | Every new call, moves for the next possible matching subsequence and set new values on the `Matcher` instance, until there's no possible matches, resulting in a `false`. 270 | 271 | 272 | ```java 273 | import java.util.regex.*; 274 | 275 | class Regex { 276 | public static void main(String args[]) { 277 | String time = "[06-03-2021 17:08:40]"; 278 | Pattern pattern = Pattern.compile("\\d{2}"); 279 | Matcher matcher = pattern.matcher(time); 280 | while(matcher.find()) { 281 | System.out.println("Matched value: " + matcher.group()); 282 | System.out.println("Start at: " + matcher.start()); 283 | System.out.println("Ends at: " + matcher.end()); 284 | } 285 | } 286 | } 287 | ``` 288 | 289 | 290 | #### `group()` 291 | As the [documentation](https://docs.oracle.com/javase/7/docs/api/java/util/regex/Matcher.html#group(int)) states: 292 | > _"Returns the input subsequence matched by the previous match._ 293 | > _This method returns a `String`; The (possibly empty) subsequence captured by the group during the previous match, or null if the group failed to match part of the input."_ 294 | 295 | This method has two overloads: 296 | 1. `group(int group)`: This parameter represents each group's numbered backreference. 297 | 2. `group(String name)`: The `name` parameter can be used to backreference named capturing groups. 298 | --- 299 | 300 | ## **Python** 301 | 302 | ### Pattern Declaration 303 | Just like `Go`, in `Python` you can either declare a pattern using the `re.compile()` method which creates a [regular expression object](https://docs.python.org/3/library/re.html#re-objects), or directly access the `re` module methods passing in the pattern as a `String`. 304 | 305 | ```python 306 | import re 307 | 308 | string_pattern = "((?:T|t)he)" 309 | regex_object = re.compile("((?:T|t)he)") 310 | ``` 311 | 312 | ### **Useful Regex Supporting API methods** 313 | 314 | #### `re.search(pattern, string, flags=0)` 315 | 316 | This method searches through the string capturing the first occurence that matches the defined pattern. 317 | 318 | This method returns a [**Match Object**](https://docs.python.org/3/library/re.html#match-objects) or **None**. 319 | 320 | ```python 321 | import re 322 | 323 | string_pattern = "((?:T|t)he)" 324 | regex_object = re.compile("((?:T|t)he)") 325 | 326 | sentence = "The quick red fox jumped over the lazy dog" 327 | 328 | match_object = re.search(string_pattern, sentence) 329 | # Or... 330 | # match_object = regex_object.search(sentence) 331 | 332 | print(match_object) 333 | ``` 334 | 335 | #### `re.match(pattern, string, flags=0)` 336 | 337 | This method works similarly to the `re.search()` method. The only difference is that it restricts the search location to the **beginning of the String**. 338 | 339 | This method returns a `Match Object` or **None**. 340 | 341 | ```python 342 | import re 343 | 344 | string_pattern = "((?:T|t)he)" 345 | regex_object = re.compile("((?:T|t)he)") 346 | 347 | sentence = "The quick red fox jumped over the lazy dog" 348 | 349 | result = re.match(string_pattern, sentence) 350 | # Or... 351 | # result = regex_object.match(sentence) 352 | 353 | print(result) 354 | 355 | ``` 356 | > ⚠ Keep in mind 357 | > 358 | > This method will always restrict the search to the beginning of the string. If you need to perform a search at the beginning of each line, use the `re.search()` method along with the `re.MULTILINE` flag. 359 | 360 | #### `re.fullmatch(pattern, string, flags=0)` 361 | 362 | This method returns a `Match Object` if the whole string is matched by the defined pattern. Otherwise, it retursn **None** 363 | 364 | ```python 365 | import re 366 | 367 | string_pattern = "\d{3}-\d{2}-\d{4}" 368 | regex_object = re.compile("\d{3}-\d{2}-\d{4}") 369 | 370 | ssn = "123-45-6789" 371 | 372 | result = re.fullmatch(string_pattern, ssn) 373 | # Or... 374 | # result = regex_object.match(sentence) 375 | 376 | print(result) 377 | ``` 378 | 379 | #### `re.split(pattern, string, maxsplit=0, flags=0)` 380 | 381 | This method split the String by the occurr­ences of the pattern. Use the `maxplit` parameter to limit the amount of occurences. 382 | 383 | Returns a `List` of all groups. 384 | 385 | ```python 386 | import re 387 | 388 | string_pattern = "[aeiou]" 389 | regex_object = re.compile("[aeiou]") 390 | 391 | sentence = "The quick brown fox jumped over the lazy dog" 392 | 393 | result = re.split(string_pattern, sentence) 394 | # Or... 395 | # result = regex_object.split(sentence) 396 | 397 | print(result) 398 | ``` 399 | 400 | #### `re.findall(pattern, string, flags=0)` 401 | 402 | This method **finds all** occurrences in string and return them as a list of strings. 403 | 404 | ```python 405 | import re 406 | 407 | string_pattern = "((?:T|t)he)" 408 | regex_object = re.compile("((?:T|t)he)") 409 | 410 | sentence = "The quick red fox jumped over the lazy dog" 411 | 412 | result = re.findall(string_pattern, sentence) 413 | 414 | print(result) 415 | ``` 416 | 417 | --- 418 | ## **Ruby** 419 | 420 | ### **Pattern Declaration** 421 | 422 | ```ruby 423 | class Playground 424 | 425 | sentence = "The quick brown fox jumped over the lazy dog" 426 | pattern = Regexp.new(/((?:T|t)he)/) 427 | pattern2 = Regexp.compile(/((?:T|t)he)/) # Alias for Regexp.new() 428 | pattern3 = /((?:T|t)he)/ # puts pattern3.instance_of? Regexp == true 429 | end 430 | ``` 431 | 432 | ### **Useful Regex Supporting API methods** 433 | 434 | #### **`String =~ Regexp`** 435 | 436 | The pattern matching operator, matches a regular expression against a string and returns an `Integer` representing the starting position of the match, or `nil` if none was found. 437 | 438 | ```ruby 439 | class Playground 440 | pattern = /\d{3}-\d{2}-\d{4}/ 441 | ssn = "123-45-6789" 442 | 443 | puts ssn =~ pattern # 0 444 | end 445 | ``` 446 | > 👀 Observation 447 | > 448 | > This value can be stored on a regular variable like so: 449 | > 450 | > ```ruby 451 | > variable = ssn =~ pattern 452 | > ``` 453 | > 454 | > However, this value has already been stored on the global `$~` variable, and it can also be accessed through the `Regexp.last_match`. 455 | 456 | #### **`String.scan(pattern)`** 457 | 458 | This method expects a pattern(`String` or `Regexp`) and iterates through in search for a match, returning an `Array` or `nil` if none was found. 459 | 460 | ```ruby 461 | class Playground 462 | sentence = "The quick red fox jumped over the lazy dog" 463 | pattern = /(?:T|t)he/ 464 | results = sentence.scan(pattern) 465 | print results 466 | 467 | 468 | sentence.scan(pattern).each do |match| 469 | puts "Found: #{match}" 470 | end 471 | end 472 | ``` 473 | 474 | Alternatively, you can use the following syntax as well: 475 | 476 | ```ruby 477 | class Playground 478 | sentence = "The quick red fox jumped over the lazy dog" 479 | pattern = /(?:T|t)he/ 480 | sentence.scan(pattern).each do |match| 481 | puts "Found: #{match}" 482 | end 483 | end 484 | ``` 485 | 486 | #### **`Regexp.match(string, start_pos)`** 487 | 488 | The Match method matches a pattern against a string capturing the first occurence. 489 | 490 | This method returns a `MatchObject` or `nil` if none was found. 491 | 492 | ```ruby 493 | class Playground 494 | sentence = "The quick red fox jumped over the lazy dog" 495 | pattern = /(?:T|t)he/ 496 | matchedData = sentence.match(pattern) 497 | print matchedData 498 | end 499 | ``` 500 | 501 | #### **`MatchData.named_captures()`** 502 | 503 | This method returns a `Hash`, pairing the **capturing groups**(keys) with their respective values. 504 | 505 | ```ruby 506 | class Playground 507 | pattern = /(?\d{3})-(?\d{2})-(?\d{4})/ 508 | ssn = "123-45-6789" 509 | 510 | result = pattern.match(ssn) 511 | result_as_hash = result.named_captures 512 | print result_as_hash # {"fst"=>"123", "scnd"=>"45", "thrd"=>"6789"} 513 | end 514 | ``` 515 | 516 | Alternatively, you can use this syntax as well: 517 | ```ruby 518 | class Playground 519 | pattern = /(?\d{3})-(?\d{2})-(?\d{4})/ 520 | ssn = "123-45-6789" 521 | 522 | result_as_hash = result.named_captures 523 | 524 | result_as_hash.each do |key, value| 525 | puts "#{key}: #{value}" 526 | end 527 | # fst: 123 528 | # scnd: 45 529 | # thrd: 6789 530 | end 531 | ``` 532 | 533 | #### **`MatchData[]`** 534 | 535 | Using this operator you have access to the matched data. Pass numbers for numbered backreference, or the capturing group name preceded by a colon. 536 | 537 | ```ruby 538 | class Playground 539 | pattern = /(?\d{3})-(?\d{2})-(?\d{4})/ 540 | ssn = "123-45-6789" 541 | 542 | result = pattern.match(ssn) 543 | puts "Full Match: #{result[0]}" 544 | puts "First Group: #{result[1]}" 545 | puts "Second Group: #{result[2]}" 546 | puts "Thrid Group: #{result[3]}" 547 | 548 | puts "Named Backreference: #{result[:fst]}" 549 | end 550 | ``` 551 | 552 | 553 | #### **`String.sub(pattern, replaceValue)`** 554 | 555 | The `sub` method is the equivalent to JavaScript's `String.prototype.replace()` method. The first parameter can be either a `Regexp` pattern or a `String` and the second parameter is the replace value. 556 | 557 | ```ruby 558 | class Playground 559 | sentence = "The quick brown fox, jumped over the lazy dog" 560 | pattern = /the/i 561 | puts sentence.sub(pattern, "THE") 562 | # THE quick brown fox, jumped over the lazy dog 563 | end 564 | ``` 565 | 566 | Notice that it only replaced the first occurence of the word **the**. The `sub` method only replaces the first occurence, and since Ruby(2.7.x) **does not** support the **global flag**, if you ever need to replace all the occurences, you need to use the gsub method. 567 | 568 | --- 569 | ## **Additional Resources** 570 | 571 | ### Reading Material 572 | 573 | - [Rexegg](http://www.rexegg.com/) 574 | - [regular-expressions.info](https://www.regular-expressions.info/javascript.html) 575 | - [javascript.info](https://javascript.info/regular-expressions) 576 | - [Mastering Regular Expressions](https://www.oreilly.com/library/view/mastering-regular-expressions/0596528124/) 577 | - [Regular Expressions Cookbook](https://www.oreilly.com/library/view/regular-expressions-cookbook/9781449327453/) 578 | 579 | ### Testing, Debugging & Visualizing 580 | - [Regex101](https://regex101.com/) 581 | - [Regexr](https://regexr.com/) 582 | - [Regexper](https://regexper.com/) 583 | --------------------------------------------------------------------------------