333

I am trying to extract a string from within a larger string where it get everything inbetween a : and a ;

Current

Str = 'MyLongString:StringIWant;'

Desired Output

newStr = 'StringIWant'
Penny Liu
  • 15,447
  • 5
  • 79
  • 98
Rob
  • 11,185
  • 10
  • 36
  • 54

26 Answers26

666

You can try this

var mySubString = str.substring(
    str.indexOf(":") + 1, 
    str.lastIndexOf(";")
);
EduardoG
  • 73
  • 1
  • 4
Babasaheb Gosavi
  • 7,735
  • 1
  • 14
  • 14
  • 4
    Trivial solution but handy especially if you want to avoid regular expressions. – Nikolay Frick Jun 24 '15 at 20:59
  • 27
    Does anyone know how I would do this for every occurence of a substring between my starting and ending string? – MarksCode Feb 26 '16 at 05:11
  • This doesn't cover many other cases (I think it's not so useful when solution is too specific). See the answer by tsds, it covers so many more cases. – Dalibor Dec 03 '20 at 12:18
222

You can also try this:

var str = 'one:two;three';    
str.split(':').pop().split(';')[0]; // returns 'two'
MysteryPancake
  • 1,365
  • 1
  • 18
  • 47
tsds
  • 8,700
  • 12
  • 62
  • 83
  • 1
    This should be the selected answer because it covers many other cases such as: having multiple characters instead of just one; finding next occurance; this solved my need and the most voted answer didn't.. I had to extract version from URL: https://somewhere.com/something/version_1.2.3/somethingElse/page and this worked like a charm. – Dalibor Dec 03 '20 at 12:15
  • This has one setback though.. if there are no : nor ; the whole str is returned :) – Dalibor Dec 06 '20 at 18:00
  • 2
    Phew! I can still keep my lambda braceless. – Marinos An Dec 09 '20 at 14:39
  • 1
    Works great for URLs – GavinBelson Nov 05 '21 at 22:38
68

Use split()

var s = 'MyLongString:StringIWant;';
var arrStr = s.split(/[:;]/);
alert(arrStr);

arrStr will contain all the string delimited by : or ;
So access every string through for-loop

for(var i=0; i<arrStr.length; i++)
    alert(arrStr[i]);
asifsid88
  • 4,631
  • 20
  • 30
  • The string I want is between [ ] and this ain't working... ex: 'MyLongString[StringIWant]'.split(/[[]]/); – Felipe Sep 12 '18 at 13:33
  • 4
    @Philippe For your use-case, use this regex `\[(.*?)\]` ---> In short you need to escape square brackets, as [ ] denotes character class in regex. – asifsid88 Sep 12 '18 at 17:50
50

@Babasaheb Gosavi Answer is perfect if you have one occurrence of the substrings (":" and ";"). but once you have multiple occurrences, it might get little bit tricky.


The best solution I have came up with to work on multiple projects is using four methods inside an object.

  • First method: is to actually get a substring from between two strings (however it will find only one result).
  • Second method: will remove the (would-be) most recently found result with the substrings after and before it.
  • Third method: will do the above two methods recursively on a string.
  • Fourth method: will apply the third method and return the result.

Code

So enough talking, let's see the code:

var getFromBetween = {
    results:[],
    string:"",
    getFromBetween:function (sub1,sub2) {
        if(this.string.indexOf(sub1) < 0 || this.string.indexOf(sub2) < 0) return false;
        var SP = this.string.indexOf(sub1)+sub1.length;
        var string1 = this.string.substr(0,SP);
        var string2 = this.string.substr(SP);
        var TP = string1.length + string2.indexOf(sub2);
        return this.string.substring(SP,TP);
    },
    removeFromBetween:function (sub1,sub2) {
        if(this.string.indexOf(sub1) < 0 || this.string.indexOf(sub2) < 0) return false;
        var removal = sub1+this.getFromBetween(sub1,sub2)+sub2;
        this.string = this.string.replace(removal,"");
    },
    getAllResults:function (sub1,sub2) {
        // first check to see if we do have both substrings
        if(this.string.indexOf(sub1) < 0 || this.string.indexOf(sub2) < 0) return;

        // find one result
        var result = this.getFromBetween(sub1,sub2);
        // push it to the results array
        this.results.push(result);
        // remove the most recently found one from the string
        this.removeFromBetween(sub1,sub2);

        // if there's more substrings
        if(this.string.indexOf(sub1) > -1 && this.string.indexOf(sub2) > -1) {
            this.getAllResults(sub1,sub2);
        }
        else return;
    },
    get:function (string,sub1,sub2) {
        this.results = [];
        this.string = string;
        this.getAllResults(sub1,sub2);
        return this.results;
    }
};

How to use?

Example:

var str = 'this is the haystack {{{0}}} {{{1}}} {{{2}}} {{{3}}} {{{4}}} some text {{{5}}} end of haystack';
var result = getFromBetween.get(str,"{{{","}}}");
console.log(result);
// returns: [0,1,2,3,4,5]
Alex C.
  • 4,021
  • 4
  • 21
  • 24
34
var s = 'MyLongString:StringIWant;';
/:([^;]+);/.exec(s)[1]; // StringIWant
otakustay
  • 11,817
  • 4
  • 39
  • 43
31

I like this method:

var str = 'MyLongString:StringIWant;';
var tmpStr  = str.match(":(.*);");
var newStr = tmpStr[1];
//newStr now contains 'StringIWant'
Oded Breiner
  • 28,523
  • 10
  • 105
  • 71
Shane Gib.
  • 411
  • 4
  • 5
  • I tested this in a SharePoint 2013 Webpart and worked great if that helps anyone in the future! – Shane Gib. May 17 '16 at 21:06
  • 3
    This may not work if the string that you want is between "(" and ")" – bravokeyl Feb 18 '18 at 10:38
  • @bravokeyl just escape the parenthesis. Like `str.match("\\((.*)\\)")`. So this will give you an array with 2 items. One with parenthesis and one with extracted parenthesis. – achchu93 Jul 12 '23 at 08:34
15

You can use a higher order function to return a 'compiled' version of your extractor, that way it's faster.

With regexes, and compiling the regex once in a closure, Javascript's match will return all matches.

This leaves us with only having to remove what we used as our markers (ie: {{) and we can use string length for this with slice.

function extract([beg, end]) {
    const matcher = new RegExp(`${beg}(.*?)${end}`,'gm');
    const normalise = (str) => str.slice(beg.length,end.length*-1);
    return function(str) {
        return str.match(matcher).map(normalise);
    }
}

Compile once and use multiple times...

const stringExtractor = extract(['{','}']);
const stuffIneed = stringExtractor('this {is} some {text} that can be {extracted} with a {reusable} function');
// Outputs: [ 'is', 'text', 'extracted', 'reusable' ]

Or single-time use...

const stuffIneed = extract(['{','}'])('this {is} some {text} that can be {extracted} with a {reusable} function');
// Outputs: [ 'is', 'text', 'extracted', 'reusable' ]

Also look at Javascript's replace function but using a function for the replacement argument (You would do that if for example you were doing a mini template engine (string interpolation) ... lodash.get could also be helpful then to get the values you want to replace with ? ...

My answer is too long but it might help someone!

Ooki Koi
  • 320
  • 4
  • 4
9

I used @tsds way but by only using the split function.

var str = 'one:two;three';    
str.split(':')[1].split(';')[0] // returns 'two'

word of caution: if therre is no ":" in the string accessing '1' index of the array will throw an error! str.split(':')[1]

therefore @tsds way is safer if there is uncertainty

str.split(':').pop().split(';')[0]
Timar Ivo Batis
  • 1,861
  • 17
  • 21
9
function substringBetween(s, a, b) {
    var p = s.indexOf(a) + a.length;
    return s.substring(p, s.indexOf(b, p));
}

// substringBetween('MyLongString:StringIWant;', ':', ';') -> StringIWant
// substringBetween('MyLongString:StringIWant;;', ':', ';') -> StringIWant
// substringBetween('MyLongString:StringIWant;:StringIDontWant;', ':', ';') -> StringIWant
bianbian
  • 548
  • 4
  • 3
9

Generic and simple:

function betweenMarkers(text, begin, end) {
  var firstChar = text.indexOf(begin) + begin.length;
  var lastChar = text.indexOf(end);
  var newText = text.substring(firstChar, lastChar);
  return newText;
}

console.log(betweenMarkers("MyLongString:StringIWant;",":",";"));
JacobTheKnitter
  • 415
  • 5
  • 7
5

Use the ‘get_between’ utility function:

get_between <- function(str, first_character, last_character) {
    new_str = str.match(first_character + "(.*)" + last_character)[1].trim()
    return(new_str)
    }

string

my_string = 'and the thing that ! on the @ with the ^^ goes now' 

usage:

get_between(my_string, 'that', 'now')

result:

"! on the @ with the ^^ goes
Cybernetic
  • 12,628
  • 16
  • 93
  • 132
4

This code above works for simple examples but can help ... Using Typescript.

Parameters

  • sentence : the string you want to get parts of
  • first : beginning character (for the initial example it would be :)
  • last : last character of your part (for the initial example it would be ;)

Output

An array of string (string[]). Returns [] if no good parts in the sentence.

Code

function getParts(sentence: string, first: string, last: string): string[] { 
  let goodParts: string[] = [];
  
  const allParts = sentence.split(first);

  allParts.forEach((part: string) => {
    if (part.indexOf(last) > -1) {
            const goodOne = (part.split(last))[0];
      goodParts = goodParts.concat(goodOne);
    }
  });
  
  return goodParts;
}

Example

const origin = "wrongString1:rightString1;wrongString2:rightString2;wrongString3:rightString3;wrongString4:rightString4;";

const result = getParts(origin, ':', ';');

console.log(result);
// ["rightString1", "rightString2", "rightString3", "rightString4"]
Hugo Bayoud
  • 149
  • 1
  • 5
3

Get string between two substrings (contains more than 1 character)

function substrInBetween(whole_str, str1, str2){
   if (whole_str.indexOf(str1) === -1 || whole_str.indexOf(str2) === -1) {
       return undefined; // or ""
  }
  var strlength1 = str1.length;
  return whole_str.substring(
                whole_str.indexOf(str1) + strlength1, 
                whole_str.indexOf(str2)
               );

   }

Note I use indexOf() instead of lastIndexOf() so it will check for first occurences of those strings

aristotll
  • 8,694
  • 6
  • 33
  • 53
beginner
  • 2,366
  • 4
  • 29
  • 53
  • 2
    Nice and very readable function. But what is the purpose of the `strlength1` variable? The value should be used inline instead. Also it's not clear which [case style](https://medium.com/better-programming/string-case-styles-camel-pascal-snake-and-kebab-case-981407998841) you are using. `strlength1` - no style, `whole_str` - snake case. – Boris Apr 21 '20 at 15:12
2

You can also use this one...

function extractText(str,delimiter){
  if (str && delimiter){
    var firstIndex = str.indexOf(delimiter)+1;
    var lastIndex = str.lastIndexOf(delimiter);
    str = str.substring(firstIndex,lastIndex);
  }
  return str;
}


var quotes = document.getElementById("quotes");

// &#34 - represents quotation mark in HTML
<div>


  <div>
  
    <span id="at">
      My string is @between@ the "at" sign
    </span>
    <button onclick="document.getElementById('at').innerText = extractText(document.getElementById('at').innerText,'@')">Click</button>
  
  </div>
  
  <div>
    <span id="quotes">
      My string is "between" quotes chars
    </span>
    <button onclick="document.getElementById('quotes').innerText = extractText(document.getElementById('quotes').innerText,'&#34')">Click</button>
  
  </div>

</div>
Meir Gabay
  • 2,870
  • 1
  • 24
  • 34
2

This could be the possible solution

var str = 'RACK NO:Stock;PRODUCT TYPE:Stock Sale;PART N0:0035719061;INDEX NO:21A627 042;PART NAME:SPRING;';  
var newstr = str.split(':')[1].split(';')[0]; // return value as 'Stock'

console.log('stringvalue',newstr)
Dino
  • 7,779
  • 12
  • 46
  • 85
Mahendren Mahisha
  • 1,072
  • 11
  • 9
1

Try this to Get Substring between two characters using javascript.

        $("button").click(function(){
            var myStr = "MyLongString:StringIWant;";
            var subStr = myStr.match(":(.*);");
            alert(subStr[1]);
        });

Taken from @ Find substring between the two characters with jQuery

Ketan Savaliya
  • 1,190
  • 9
  • 11
1

A small function I made that can grab the string between, and can (optionally) skip a number of matched words to grab a specific index.

Also, setting start to false will use the beginning of the string, and setting end to false will use the end of the string.

set pos1 to the position of the start text you want to use, 1 will use the first occurrence of start

pos2 does the same thing as pos1, but for end, and 1 will use the first occurrence of end only after start, occurrences of end before start are ignored.

function getStringBetween(str, start=false, end=false, pos1=1, pos2=1){
  var newPos1 = 0;
  var newPos2 = str.length;

  if(start){
    var loops = pos1;
    var i = 0;
    while(loops > 0){
      if(i > str.length){
        break;
      }else if(str[i] == start[0]){
        var found = 0;
        for(var p = 0; p < start.length; p++){
          if(str[i+p] == start[p]){
            found++;
          }
        }
        if(found >= start.length){
          newPos1 = i + start.length;
          loops--;
        }
      }
      i++;
    }
  }

  if(end){
    var loops = pos2;
    var i = newPos1;
    while(loops > 0){
      if(i > str.length){
        break;
      }else if(str[i] == end[0]){
        var found = 0;
        for(var p = 0; p < end.length; p++){
          if(str[i+p] == end[p]){
            found++;
          }
        }
        if(found >= end.length){
          newPos2 = i;
          loops--;
        }
      }
      i++;
    }
  }

  var result = '';
  for(var i = newPos1; i < newPos2; i++){
    result += str[i];
  }
  return result;
}
SwiftNinjaPro
  • 787
  • 8
  • 17
1

To get all substring.

var out = []; 'MyLongString:StringIWant;'
.replace(/(:)\w+(;)+/g, (e) => {
    out.push(e.replace(':', '').replace(';', ''))
    return e;
});
console.log(out[0])
Leonardo Pineda
  • 990
  • 8
  • 10
1

You can use this function-

function getStringInBetween(string, start , end) {
    // start and end will be excluded
    var indexOfStart = string.indexOf(start)
    indexOfStart = indexOfStart + start.length;
    var newString = string.slice(indexOfStart)
    var indexOfEnd = newString.indexOf(end)
    return newString.slice(0, indexOfEnd)
}

For ex -

let string = "<div class = 'mice'> I know how to code </div>"
let start = "<div class = 'mice'> "
let end = " </div>"
//then, getStringInBetween(string, start, end) returns "I know how to code"
0

If you want to extract all substrings from a string, that occur between two delimiters (different or same), you can use this function. It returns an array with all substrings found:

function get_substrings_between(str, startDelimiter, endDelimiter) 
{
    var contents = [];
    var startDelimiterLength = startDelimiter.length;
    var endDelimiterLength = endDelimiter.length;
    var startFrom = contentStart = contentEnd = 0;
    
    while(false !== (contentStart = strpos(str, startDelimiter, startFrom))) 
    {
        contentStart += startDelimiterLength;
        contentEnd = strpos(str, endDelimiter, contentStart);
        if(false === contentEnd) 
        {
            break;
        }
        contents.push( str.substr(contentStart, contentEnd - contentStart) );
        startFrom = contentEnd + endDelimiterLength;
    }

    return contents;
}

// https://stackoverflow.com/a/3978237/1066234
function strpos(haystack, needle, offset) 
{
    var i = (haystack+'').indexOf(needle, (offset || 0));
    return i === -1 ? false : i;
}

// Example usage
var string = "We want to extract all infos (essential ones) from within the brackets (this should be fun).";
var extracted = get_substrings_between(string, '(', ')');
console.log(extracted); 
// output: (2) ["essential ones", "this should be fun"]

Orginally from PHP by raina77ow, ported to Javascript.

Avatar
  • 14,622
  • 9
  • 119
  • 198
0
var str = '[basic_salary]+100/[basic_salary]';
var arr = str.split('');
var myArr = [];
for(var i=0;i<arr.length;i++){
    if(arr[i] == '['){
        var a = '';
        for(var j=i+1;j<arr.length;j++){
            if(arr[j] == ']'){
                var i = j-1;
                break;
            }else{
                a += arr[j];
            }
        }
        myArr.push(a);
    }
    var operatorsArr = ['+','-','*','/','%'];
    if(operatorsArr.includes(arr[i])){
        myArr.push(arr[i]);
    }
    var numbArr = ['0','1','2','3','4','5','6','7','8','9'];
    if(numbArr.includes(arr[i])){
        var a = '';
        for(var j=i;j<arr.length;j++){
            if(numbArr.includes(arr[j])){
                a += arr[j];
            }else{
                var i = j-1;
                break;
            }
        }
        myArr.push(a);
    }
}
myArr = ["basic_salary", "+", "100", "/", "basic_salary"]
Muhammad Umar
  • 95
  • 1
  • 5
0

Here's something I just made.

Note that the function will return everything after start if end is not found after start. It also expects there's only one occurrence of of start and end, and if there are multiple - it will only consider the first.

License: Public domain

/**
 * Extracts a string from `source` that is placed between `start` and `end`. The function
 * considers only one instance of start and before, or the first instance and does not support
 * multiple occurences otherwise. If end string is not found, it will return everything after
 * `start` to the end of the string.
 */
export function stringBetween(source, start, end) {
  if (source.indexOf(start) === -1) {
    return null;
  }

  const sourceSplitByStartString = source.split(start);

  // Note: If start string is the very first occurence in source string, the result will be an
  // array where the first item is an empty string and the next item is of interest.

  if (
    sourceSplitByStartString.length === 1
    || sourceSplitByStartString[1] === ''
  ) {
    // It means that start is either the entire string or is at the very end of the string, so there
    // is not anything between
    return '';
  }

  const afterStart = sourceSplitByStartString[1];

  // If the after separator is not found, return everything after the start separator to the end
  // of the string
  if (afterStart.indexOf(end) === -1) {
    return afterStart;
  }

  const afterStartSplitByEnd = afterStart.split(end);

  if (afterStartSplitByEnd[0] === '') {
    return '';
  }

  return afterStartSplitByEnd[0];
}

Tests:

import { stringBetween } from './string';

describe('string utlities', () => {
  describe('stringBetween', () => {
    it('Extracts a substring between 2 other substrings', () => {
      const sample1 = stringBetween('Black cat climbed the tree fast.', 'cat ', ' the tree');
      expect(sample1).toBe('climbed');

      const sample2 = stringBetween('Black cat climbed the tree fast.', 'Black ', ' fast.');
      expect(sample2).toBe('cat climbed the tree');
    });

    it('extracts everything after start if end is not found', () => {
      const sample2 = stringBetween('Black cat climbed the tree fast.', 'Black ', 'not-there');
      expect(sample2).toBe('cat climbed the tree fast.');
    });

    it('returns empty string if start string occurs at the end', () => {
      const sample = stringBetween('Black cat climbed the tree fast.', 'fast.', 'climbed');
      expect(sample).toBe('');
    });

    it('returns empty string if start string is the entire string', () => {
      const sample = stringBetween('Black cat', 'Black cat', 'climbed');
      expect(sample).toBe('');
    });

    it('returns empty string if there is not anything between start and end', () => {
      const sample = stringBetween('Black cat climbed the tree fast.', 'climbed ', 'the tree');
      expect(sample).toBe('');
    });

    it('returns null if start string does not exist in the source string', () => {
      const sample = stringBetween('Black cat climbed the tree fast.', 'not-there ', 'the tree');
      expect(sample).toBe(null);
    });
  });
});

Maciej Krawczyk
  • 14,825
  • 5
  • 55
  • 67
0

Here's a reusable function that allows you to make the returned substring inclusive or exclusive and optionally trim it afterwards:

function get_substring(full_string, substring_1, substring_2, inclusive, trim)
{
    if (full_string === null) { return null; };
    let substring_1_start = full_string.indexOf(substring_1);
    if (substring_1_start === -1 ) { return null; }
    let substring_2_start = full_string.indexOf(substring_2, substring_1_start);
    if (substring_2_start === -1 ) { return null; }
    let substring_1_end = substring_1_start + substring_1.length;
    let substring_2_end = substring_2_start + substring_2.length;
    let return_string = inclusive ? (full_string.substring(substring_1_start, substring_2_end)) : (full_string.substring(substring_1_end, substring_2_start));
    return trim ? return_string.trim() : return_string;
}

Usage examples:

//Returns 'cake and ice cream'
get_substring('I like cake and ice cream', 'cake', 'cream', true, true);

//Returns ' and ice '
get_substring('I like cake and ice cream', 'cake', 'cream', false, false);

//Returns 'and ice'
get_substring('I like cake and ice cream', 'cake', 'cream', false, true);

//Returns null
get_substring('I like cake and ice cream', 'cake', 'cookies', false, false);

//Returns null
get_substring('I like cake and ice cream', null, 'cream', false, false);
Pikamander2
  • 7,332
  • 3
  • 48
  • 69
0

Here is a solution using a loop

const extractBetween = (str, separator) => {
let output = [];
let next_index = str.indexOf(separator)

while (next_index !== -1) {
    let after_next_index = str.indexOf(separator, next_index + separator.length)
    if (after_next_index !== -1)
        output.push(str.substring(next_index + separator.length, after_next_index))

    next_index = str.indexOf(separator, after_next_index + separator.length)

}

return output;

}

Hope this helps.

Nazim.A
  • 101
  • 1
  • 4
0

I believe this is the simplest and likely the fastest and works with strings, not just character delimeters

const result = ('MyLongString:StringIWant;'.split(":")[1] ||"").split(";")[0]
document.writeln(result)
chad steele
  • 828
  • 9
  • 13
-1

Following Function gets the first match


function getStringBetween(x: string, start: string, end: string) {
  const regex = new RegExp(`${start}(.*?)${end}`)

  if (regex.test(x)) {
    return regex.exec(x)![1]
  } else return undefined
}

Jest Tests


test("getStringBetween", () => {
  const result = getStringBetween("<em> Jai Ram</em>", "<em>", "</em>")
  expect(result).toEqual(" Jai Ram")
  const result1 = getStringBetween(
    "hare Jai Ram hare hare hare",
    "hare",
    "hare"
  )
  expect(result1).toEqual(" Jai Ram ")
})

Chetan Jain
  • 236
  • 6
  • 16