205

How do I strip leading and trailing spaces from a string?

For example, " dog " should become "dog".

Mateen Ulhaq
  • 24,552
  • 19
  • 101
  • 135
rawrrrrrrrr
  • 3,647
  • 7
  • 28
  • 33
  • 31
    This function is rathern known as `trim`. See https://developer.mozilla.org/En/Core_JavaScript_1.5_Reference/Global_Objects/String/Trim – Gumbo Sep 13 '09 at 15:57
  • 1
    @Gumbo: trim is a bit newer, and may not be supported across browsers. Don't know, but you can never tell with cross browser support. – David Andres Sep 13 '09 at 16:10

8 Answers8

237

Use this:

if(typeof(String.prototype.trim) === "undefined")
{
    String.prototype.trim = function() 
    {
        return String(this).replace(/^\s+|\s+$/g, '');
    };
}

The trim function will now be available as a first-class function on your strings. For example:

" dog".trim() === "dog" //true

EDIT: Took J-P's suggestion to combine the regex patterns into one. Also added the global modifier per Christoph's suggestion.

Took Matthew Crumley's idea about sniffing on the trim function prior to recreating it. This is done in case the version of JavaScript used on the client is more recent and therefore has its own, native trim function.

Christoph
  • 164,997
  • 36
  • 182
  • 240
David Andres
  • 31,351
  • 7
  • 46
  • 36
  • 3
    see http://blog.stevenlevithan.com/archives/faster-trim-javascript for some performance data – Christoph Sep 13 '09 at 16:35
  • 2
    to be compatible with the ECMA spec, `trim()` has to cast `this` to type string, ie you'll have to change `this.replace(...)` to `String(this).replace(...)` or `('' + this).replace(...)`; this allows to `call()` or `apply()` the function to non-string values – Christoph Sep 13 '09 at 19:14
  • @Christoph: do you mean to say within the String.prototype.trim() = ... function definition? I would have expected "this" to already refer to a string, as this is a prototypal function extending the String type. – David Andres Sep 13 '09 at 19:44
  • 1
    @David: yes, within the function; the ECMA spec allows `trim()` to be called on non-string objects, eg `String.prototype.trim.apply(42)` or `MyObj.prototype.trim = String.prototype.trim; new MyObj().trim();` – Christoph Sep 13 '09 at 19:57
  • @Christoph, can we get by by 42.toString() or 42 + ""? – David Andres Sep 13 '09 at 20:10
  • yes, but if you want to conform to the spec, you'll have to put the conversion into `trim()` (as I already explained 3 comments ago ;)); also, it's better to use `String(42)` instead of `42.toString()` as the former won't create an unneeded wrapper object and is the canonical way to cast to type string – Christoph Sep 13 '09 at 20:24
  • 1
    @David: otherwise, `String.prototype.trim.apply(foo)` will throw an error if `foo` doesn't have a `replace()` method; the spec allows such a use: "The trim function is intentionally generic; it does not require that its `this` value be a String object. Therefore, it can be transferred to other kinds of objects for use as a method." – Christoph Sep 13 '09 at 21:03
  • @Christoph: I believe the only way for the "this" instance to not have a replace method, or at least to have a different replace method, would be due to user intervention (assigning a different function to the instance.replace property). In this case, I understand your point. I just want to be sure I understand your statement though, because I can't understand how a String would need to casted back to a String for any other reason than what I've written here. – David Andres Sep 13 '09 at 21:10
  • 3
    Note that `/\s/` will not strip all whitespace characters defined by ES3 spec. I recently wrote about the way browsers handle `/\s/` - http://thinkweb2.com/projects/prototype/whitespace-deviations/ - and how to work around it. – kangax Sep 13 '09 at 21:21
  • 3
    Curiously enough the original two-regex version (`replace(/^\s+/, '').replace(/\s+$/, '');`) is actually slightly faster in many browsers, so you shouldn't choose the one-regex version out of performance concerns. Pick whichever you find more readable. – bobince Sep 14 '09 at 01:47
  • @bobince: This makes sense. Alternation probably slows down the regex engine somewhat and there might be a lack of optimization for it. – David Andres Sep 14 '09 at 12:24
  • Why is /\b\s+|\s+\b/g not working? – most venerable sir Jun 11 '17 at 17:41
  • @user132522: are you trying to collapse excess whitespace into a single space with that pattern? If so, what text does it not work against? – David Andres Jun 28 '17 at 05:27
152

For jquery users, how about $.trim(s)

Constantinius
  • 34,183
  • 8
  • 77
  • 85
user638373
  • 1,545
  • 1
  • 9
  • 2
116

Gumbo already noted this in a comment, but this bears repeating as an answer: the trim() method was added in JavaScript 1.8.1 and is supported by all modern browsers (Firefox 3.5+, IE 9, Chrome 10, Safari 5.x), although IE 8 and older do not support it. Usage is simple:

 "  foo\n\t  ".trim() => "foo"

See also:

lambshaanxy
  • 22,552
  • 10
  • 68
  • 92
15

Here's the function I use.

function trim(s){ 
  return ( s || '' ).replace( /^\s+|\s+$/g, '' ); 
}
Mic
  • 24,812
  • 9
  • 57
  • 70
12

A better polyfill from the MDN that supports removal of BOM and NBSP:

if (!String.prototype.trim) {
  String.prototype.trim = function () {
    return this.replace(/^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g, '');
  };
}

Bear in mind that modifying built-in prototypes comes with a performance hit (due to the JS engine bailing on a number of runtime optimizations), and in performance critical situations you may need to consider the alternative of defining myTrimFunction(string) instead. That being said, if you are targeting an older environment without native .trim() support, you are likely to have more important performance issues to deal with.

Bardi Harborow
  • 1,803
  • 1
  • 28
  • 41
9

Steven Levithan once wrote about how to implement a Faster JavaScript Trim. It’s definitely worth a look.

Gumbo
  • 643,351
  • 109
  • 780
  • 844
7

If you're already using jQuery, then you may want to have a look at jQuery.trim() which is already provided with jQuery.

AJMansfield
  • 4,039
  • 3
  • 29
  • 50
Filip Dupanović
  • 32,650
  • 13
  • 84
  • 114
6

If, rather than writing new code to trim a string, you're looking at existing code that calls "strip()" and wondering why it isn't working, you might want to check whether it attempts to include something like the prototypejs framework, and make sure it's actually getting loaded.
That framework adds a strip function to all String objects, but if e.g. you upgraded it and your web pages are still referring to the old .js file it'll of course not work.

Eric
  • 5,137
  • 4
  • 34
  • 31