4

I have a jQuery function with a user input text variable sel. I display the variable like this:

jQuery(this).parent().prev().find('.js-trigger-add-tag-target').text(sel);

Works fine.

If the variable begins or ends with any of these characters:

.,?!'"

I want to to strip those very characters. For example, if sel is:

'Hello world, josh's car.,'

I want to strip it to:

Hello world, josh's car

How do I do this in jQuery/javascript? Maybe regex?

Henrik Petterson
  • 6,862
  • 20
  • 71
  • 155

2 Answers2

12

You can use String#replace with RegEx

var regex = /^[.,?!'"]+|[.,?!'"]+$/g;
text = text.replace(regex, '');

RegEx Explanation:

  1. ^: Starts of the line anchor
  2. $: End of the line anchor
  3. [.,?!'"]+: Match any of the characters in the character class [ and ] that occur one or more times in any order
  4. |: OR condition/alteration in the RegEx
  5. g: Global flag

RegEx101 Live Demo

var regex = /^[.,?!'"]+|[.,?!'"]+$/g; // Note that you don't need `m` flag here

var resultEl = document.getElementById('output');
document.getElementById('myInput').addEventListener('keyup', function() {
  resultEl.innerHTML = this.value.replace(regex, '');
}, false);
<input type="text" id="myInput" placeholder="Type something" />

<div id="output">You'll see output here</div>

From OP's comment

How do I adjust the regex so that it removes characters if the variable ends with 's? For example, if the variable is John's, it will become John

The RegEx can be modified a bit to match 's at the end of the string.

The character class can be make lazy/non-greedy and adding 's as optional group at the end of string.

/^[.,?!'"]+|[.,?!'"]*?(?:'s)?$/

Adding ? in [.,?!'"]*? will make the match lazy. (?:) is non-capturing group and adding ? in (?:'s)? will make the 's optional.

RegEx Demo

Or, as @Daniel Cheung said in the comment, you can also use

/^[.,?!'"]+|(?:[.,?!'"]|'s)+$/

RegEx Demo

Update:

To remove spaces \s can be added in the character class. Or String#trim can also be used after `replace.

/^[.,?!'"\s]+|[.,?!'"\s]+$/
         ^^          ^^

RegEx Demo


As stated in comment by @Casimir et Hippolyte, you can use ^[\W_]+|[\W_]+$ to remove all the special characters at the beginning and end of the string.

Community
  • 1
  • 1
Tushar
  • 85,780
  • 21
  • 159
  • 179
  • **Very** nice! I have a question. How do I adjust the regex so that it removes characters if the variable ends with **'s**? For example, if the variable is **John's**, it will become **John** – Henrik Petterson Feb 13 '16 at 13:02
  • @HenrikPetterson `^[.,?!'"]+|(?:[.,?!'"]|'s)+$` – Daniel Cheung Feb 13 '16 at 13:04
  • 2
    This is great. I will accept this answer and bounty it 50 points! Just one final problem. If the text has space at the end or beginning, it doesn't work. Can you adjust the regex to ignore space at beginning or end? – Henrik Petterson Feb 13 '16 at 14:01
  • 1
    @HenrikPetterson You just have to add `\s` in the character class. [`^[.,?!'"\s]+|[.,?!'"\s]+$`](https://regex101.com/r/dX8xL5/6) – Tushar Feb 13 '16 at 14:03
  • You can be more radical using `/^[\W_]+|[\W_]+$/g` – Casimir et Hippolyte Feb 18 '16 at 12:03
  • 1
    @CasimiretHippolyte That can be done if OP want to delete all special characters except `_`. As OP has stated the characters to remove, I think it's better to remove only those characters. – Tushar Feb 18 '16 at 13:14
  • I understand, note that _ is included (it will be removed too). – Casimir et Hippolyte Feb 18 '16 at 13:18
  • @CasimiretHippolyte Added that. In case if OP/other users wants to remove all special characters. – Tushar Feb 18 '16 at 13:33
  • @Tushar is correct, only want to remove the said characters. A lot of unicode characters in my code. Bounty rewarded! – Henrik Petterson Feb 19 '16 at 20:43
0

I'd prefer a no regex solution simply because the decision "tree" within regex engines is much bigger. and especially because the regexes used for trimming contain query characters which lead to backtracking within the regex engine. such engines often compile the pattern into byte-code, resembling machine instructions. the engine then executes the code, jumping from instruction to instruction. when an instruction fails, it then back-tracks to find another way to match the input. ergo a lot more going on than necessary.

Here is a solution that I personally find more readable and is faster.

function trimByChars(string, characters) {
  const first = [...string].findIndex(char => !characters.includes(char));
  const last = [...string].reverse().findIndex(char => !characters.includes(char));
  return string.substring(first, string.length - last);
}
const chars = ["'", '"', ',', '?', '!', '.'];
trimByChars("'Hello world, josh's car.,'", chars);
Robin F.
  • 1,137
  • 11
  • 19