Thousands separator for integers in javascript - javascript

I have the following
How do I convert OrderID to thousands separator i.e., 100,000??
I'm doing it this way but it's not working:
var thousandseparator = [
"QRDER_QTY", "EXEC_QTY", "AVG_PX", "NOTIONAL_USD", "LIMIT_PX", "LIQ_CONSUMPTION"
];
for(var i = 0; i < json.length; i++) {
var obj = json[i];
for(key in obj) {
if(thousandseparator.indexOf(key) != -1) {
obj[key] = Number(obj[key].toString().toLocaleString());
}
}
}
Also, I'm converting each element to integer like this:
var jsondata = document.getElementById("jsonArray").value;
var json = JSON.parse(jsondata);
var parsedData = json.map(function(obj) {
return Object.keys(obj).reduce(function(memo, key) {
var value = obj[key];
//console.log(value);
memo[key] = isNumeric(value) ? Number(value) : value;
//localStorage.setItem("storeditem", value);
return memo;
}, {})
});
But on doing so, the decimals like 2.40 are converted to 2.4. How do I make it 2.40 only??

Here is how to use toLocaleString() (I've cut down your sample to just the essentials)
var obj = {
"ROOT_ORDER_ID": "735422197553491",
"AVG_PX": "93.6586",
"NOTIONAL_USD": "477940",
"LIQ_CONSUMPTION": "15.21",
"EXEC_QTY": "5103",
"LIMIT_PX": "93.6100",
"ORDER_QTY": "5103"
}
var thousandseparator = [
"ORDER_QTY", "EXEC_QTY", "AVG_PX", "NOTIONAL_USD", "LIMIT_PX", "LIQ_CONSUMPTION"
];
for(key in obj) {
if(thousandseparator.indexOf(key) != -1) {
obj[key] = Number(obj[key]).toLocaleString();
}
}
console.log(obj)
You want to use it on a number, hence you first want to do Number(obj[key]) and then call .toLocaleString() on the result, however your code was doing the operation in reverse.
As for your second question - you cannot have a formatted numeric value. JavaScript shows numbers in the most "convenient" way possible, although that's not the best way. In general, any extra zeroes in the fractional part will be hidden and numbers that are too long will be shortened to scientific notation (for example 1e24).
If you want to display numeric data formatted, it would have to be done as a string. If you want to show an exact number of decimal places, then use Number#toFixed() which returns a string:
var pi = 3.141592;
console.log(pi, typeof pi);
var shortPi = pi.toFixed(2);
console.log(shortPi, typeof shortPi);
var money = 3.50;
console.log(money, typeof money);
var formattedMoney = money.toFixed(2);
console.log(formattedMoney, typeof formattedMoney);

Try replacing:
obj[key] = Number(obj[key].toString().toLocaleString());
with:
obj[key] = Number(obj[key]).toLocaleString();

Related

what is the best way to extract variables with '=' from a string in javascript

I want to extract the variables names from a string like this: "foo=valor bar=second", and so on.
To return:
{
foo: "valor",
bar: "second",
...
}
You can use Regex Look Aheads to check for a variable name that is preceded by an = symbol
var str = "foo=valor bar=second";
var varRegex = /\w+(?=(\s)*(\=))/g;
var valueRegex = /(?<=(\=)[\s'"]*)\w+/g;
var varArr = str.match(varRegex);
var valueArr = str.match(valueRegex);
console.log(valueArr);
let obj = {};
for(let i in varArr) {
obj[varArr[i]] = valueArr[i];
}
console.log(obj);
var str = "foo=valor,bar=second";
var obj = {};
str.split(",").forEach(
function(item){
if(item){
var vars = item.split("=");
obj[vars[0]] = vars[1]
}
});
console.log(obj)
Different approach from the previous answer: You can split the string on spaces and then map the result array, splitting on the equal sign to create your object (left side is property, right side is value)
If you need it your specific format you can reduce it to convert the array into one big object with all the values
let a = "foo=valor bar=second"
console.log(a.split(' ').map((i,v) => { return JSON.parse(`{"${i.split('=')[0]}": "${i.split('=')[1]}"}`);}))
let b = a.split(' ').map((i,v) => { return JSON.parse(`{"${i.split('=')[0]}": "${i.split('=')[1]}"}`);})
console.log(b.reduce(function(acc, x) {
for (var key in x) acc[key] = x[key];
return acc;
}));
Not necessarily the quickest answer (in terms of speed of submission), but less regular expressions to maintain and less variables to store.
function toJSON(str) {
const regex = /(\w+)\=(\w+)\s*/g;
let result = {};
let match;
while (match = regex.exec(str)) {
result[match[1]] = match[2];
}
return result;
}
console.log(toJSON("foo=valor bar=second"));

How can I capture a hash to Object in functional JavaScript?

I'm writing a piece of code in JavaScript for modern browser. I'm not using lodash or underscore as we want to keep the library as small as possible.
For example,
If the url comes like this. http://something.com/#hash=value
And the app is configured to capture key hash then the result would be this. Nothing fancy. I was just wondering if there's a better way or simple way to do this.
{
'hash': 'value'
}
The code
var config = Object.assign({}, {
capturedHashParams: ['hash']
});
var hashValue = '#hash=value1'.substr(1);
var capturedHashParams = {};
if (config.capturedHashParams && Array.isArray(config.capturedHashParams)) {
var splitedHash = hashValue.split('=');
if (splitedHash.length > 0) {
var key = splitedHash[0] || '';
var value = splitedHash[1] || '';
if (key && value) {
config.capturedHashParams.forEach(function(hp) {
if (hp.toLowerCase().indexOf(key.toLowerCase()) > -1) {
capturedHashParams[key] = value;
}
});
}
}
}
console.log(capturedHashParams);
https://jsfiddle.net/c92p0rfm/2/
i think you are watching for something like this:
var output = [];
var hashString = window.location.hash;
var hashArray = hash.split('&');
for(var index = 0; index < hashArray.length; index++){
var text = hashArray[index];
var tempArray= text.split('=');
var object = {
id: tempArray[0],
value: tempArray[1]
};
output[index] = object;
}
now output looks like this:
[
{
id: "hash",
value: "value"
}
]
Your question is somewhat ambiguous. It appears that you want to extract key/value pairs from an url hash and return as a JavaScript object. I am bit uncertain about whether you want to extract all key/value pairs or only those provided in a config object. I am also a bit uncertain as to whether you want a solution within a strict functional programming paradigm, or just a plain solution with a small code footprint. I will assume the latter.
A straightforward approach to capture all key/value pairs:
var url = 'http://something.com/#hash=value&anotherHash=value';
//extract key=value pairs from url
var params = url.split('#').pop().split('&');
//assign to data object
for(var data = {}, i = 0, temp; i < params.length; i++){
// extract array [key, value]
temp = params[i].split('=');
// assign to data object
data[temp[0]] = temp[1];
}
console.log(data);
A more compact solution to do the same with .reduce():
var url = 'http://something.com/#hash=value&anotherHash=value';
var data = url
.split('#')
.pop()
.split('&')
.reduce(function(obj, keyval){
keyval = keyval.split('=');
obj[keyval[0]] = keyval[1];
return obj;
}, {});
console.log(data)
If you want to configure which keys to extract:
var url = 'http://something.com/#hash=value&anotherHash=value&notThisHash=value';
//config object
var keysToCapture = [
'hash',
'anotherHash'
];
var data = url
.split('#')
.pop()
.split('&')
.reduce(function(obj, keyval){
keyval = keyval.split('=');
if(keysToCapture.indexOf(keyval[0]) > -1){
obj[keyval[0]] = keyval[1];
}
return obj;
}, {});
console.log(data)
Which you could capture in a reusable function like this:
function extractParamsObject(url, keysToCapture){
return url
.split('#')
.pop() //hash/fragment: everything after the last #
.split('&')
.reduce(function(obj, keyval){
keyval = keyval.split('=');
if(keysToCapture.indexOf(keyval[0]) > -1){
obj[keyval[0]] = keyval[1];
}
return obj;
}, {});
}
console.log(extractParamsObject(
'http://something.com/#hash=value&anotherHash=value&notThisHash=value',
['hash', 'anotherHash']
));

how to cut a string in javascript

I'm receiving a String like this:
"45,21,555,64,94,796,488,\n " the \n means new line
is there a way to cut the string based on "," and getting only the "number".
I could do it C but how can I search for a character in JavaScript.
thanks for any hint
var parts = "45,21,555,64,94,796,488,\n ".split(',').filter(function(val) {
var num = parseInt(val, 10);
return !isNaN(num) && toString.call(num) === '[object Number]';
});
// parts: ["45", "21", "555", "64", "94", "796", "488"]
This is taking your String and splitting it into an Array based on a delimiter (',') and then running it through a filter function to remove anything that does not evaluate to a valid Number.
See String.prototype.split and Array.prototype.filter.
If you actually want to then convert those values to Numbers, you could chain a map call:
var parts = "45,21,555,64,94,796,488,\n ".split(',')
.filter(function(val) {
var num = parseInt(val, 10);
return !isNaN(num) && toString.call(num) === '[object Number]';
})
.map(function(val) {
return parseInt(val, 10);
});
// parts: [45, 21, 555, 64, 94, 796, 488]
Yes, like this:
var myString = "45,21,555,64,94,796,488,\n ";
var splitStrings = string.split(",");
console.log(splitStrings); //Should log an array to the console, containing only your strings e.g. [45,21,555,64,94,796,488,\n]
This returns an array of strings, split by the character you passed in. You can read more on this method here: http://www.w3schools.com/jsref/jsref_split.asp
After that, you can parse your array to remove anything you don't want like the new line character, or use a filter method to do it inline as detailed in another answer
You can use string.split(splitChar) to split. Then you can use .map or .filter to convert items to number.
var str = "45,21,555,64,94,796,488,\n ";
var arr = str.split(",");
document.write("Array: <pre>"+JSON.stringify(arr)+"</pre>");
var nums = arr.map(function(item){
return parseInt(item);
});
document.write("Numbers: <pre>"+JSON.stringify(nums)+"</pre>");
If you are wanting just the numbers as an array you could do this.
var str = "45,21,555,64,94,796,488,\n ";
var arr = str.split(","); //Make the string into an array
var len = arr.length;
for(var i=0;i<len;i++)
{
try
{
arr[i] = parseInt(arr[i]); // convert the numbers to ints
}
catch(e)
{
arr[i] = null;
}
}
As the fact that strings are just arrays, you can do it this way (a bit more comprehensive, in my opinion):
function noCommas(a)
{
var b = '';
for (var i = 0; i < a.length; i++)
{
if (a[i] != ',') //&& a[i]!= String.fromCharCode(10)) If you want no new lines too
{
b += a[i];
} else
{
//break; -> In case you only want the first value
}
}
return parseInt(b); //To return the value as an integer
}
noCommas('1234,6789'); // returns 12346789
I missunderstood the question, so here's my fixed code:
function noCommas(a)
{
var b = [];
var tempNum = '';
for (var i = 0; i < a.length; i++)
{
if (a[i] != ',' && i != a.length - 1)
{
tempNum += a[i];
} else
{
b.push(parseInt(tempNum))
tempNum = '';
}
}
return b;
}
now if you do noCommas('123,345,324234')[2] it would return 324234.

Javascript: Quickly lookup value in object (like we can with properties)

I have an object that has pairs of replacement values used for simple encoding / decoding (not for security, just for a convenience; too complicated to explain it all here). It's in the form
var obj = {x: y,
x: y,
...
};
where 'x' is the value when encoded and 'y' is the decoded value.
Decoding is simple: I loop through the characters of the string, and look up the charAt(i) value in the object via brackets: obj[ str.charAt(i) ]. (I'm leaving out the check to see whether we need an uppercase or lowercase version (all key/values in the object are lowercase), but that's simple enough.)
To encode, I of course have to look for the value in the object, rather than the property. Currently, I'm looping through the properties with a for ... in ... loop and checking the values against the charAt(i) value. My current code is:
var i, j,
output = '',
str = 'Hello World!',
obj = {'s':'d',
'm':'e',
'e':'h',
'x':'l',
'z':'o',
'i':'r',
'a':'w',
'o':'!',
'-':' '};
for (i = 0; i < str.length; i++) {
for (j in obj) {
if (Object.prototype.hasOwnProperty.call(obj, j) &&
Object.prototype.propertyIsEnumerable.call(obj, j)) {
if (obj[j] === str.charAt(i)) {
output += j;
break;
} else if (obj[j].toUpperCase() === str.charAt(i)) {
output += j.toUpperCase();
break;
}
}
}
}
alert(output);
I innately feel like there should be a more efficient way of doing this. (Of course having a reversed object, {y: x}, is an option. But not a good one.) Is this the best way, or is there a better? In essence, I'd love to be able to do var prop = obj[value] just like I can do var value = obj[prop].
It's more efficient to loop just once beforehand to create a reverse map:
var str = "Hello World!",
output = '',
map = {
"s":"d", "m":"e",
"e":"h", "x":"l",
"z":"o", "i":"r",
"a":"w", "o":"!",
"-":" "
},
reverseMap = {}
for (j in map){
if (!Object.prototype.hasOwnProperty.call(map, j)) continue
reverseMap[map[j]] = j
}
output = str.replace(/./g, function(c){
return reverseMap[c] || reverseMap[c.toLowerCase()].toUpperCase()
})
console.log(output)
Instead of doing str.length * map.length, you'll do map.length + str.length operations.
A reverse encoder would make more sense, but you can write a replace function without all the hasOwnProperty etc.tests.
var str= 'Hello World!',
obj={
's':'d',
'm':'e',
'e':'h',
'x':'l',
'z':'o',
'i':'r',
'a':'w',
'o':'!',
'-':' '
}
str= str.replace(/./g, function(w){
for(var p in obj){
if(obj[p]=== w) return p;
if(obj[p]=== w.toLowerCase()) return p.toUpperCase();
};
return w;
});
returned value: (String) Emxxz-Azixso
You can create a reversed version of the mapping programmatically (instead of by hand) and use it instead.
var rev = {}
for (key in obj)
rev[obj[key]] = key
If you're looking for array keys check here.
https://raw.github.com/kvz/phpjs/master/functions/array/array_keys.js
function array_keys (input, search_value, argStrict) {
var search = typeof search_value !== 'undefined', tmp_arr = [], strict = !!argStrict, include = true, key = '';
if (input && typeof input === 'object' && input.change_key_case) {
return input.keys(search_value, argStrict);
}
for (key in input) {
if (input.hasOwnProperty(key)) {
include = true;
if (search) {
if (strict && input[key] !== search_value) include = false;
else if (input[key] != search_value) include = false;
}
if (include) tmp_arr[tmp_arr.length] = key;
}
}
return tmp_arr;
}

The $.param( ) inverse function in JavaScript / jQuery

Given the following form:
<form>
<input name="foo" value="bar">
<input name="hello" value="hello world">
</form>
I can use the $.param( .. ) construct to serialize the form:
$.param( $('form input') )
=> foo=bar&hello=hello+world
How can I deserialize the above String with JavaScript and get a hash back?
For example,
$.magicFunction("foo=bar&hello=hello+world")
=> {'foo' : 'bar', 'hello' : 'hello world'}
Reference: jQuery.param( obj ).
You should use jQuery BBQ's deparam function. It's well-tested and documented.
This is a slightly modified version of a function I wrote a while ago to do something similar.
var QueryStringToHash = function QueryStringToHash (query) {
var query_string = {};
var vars = query.split("&");
for (var i=0;i<vars.length;i++) {
var pair = vars[i].split("=");
pair[0] = decodeURIComponent(pair[0]);
pair[1] = decodeURIComponent(pair[1]);
// If first entry with this name
if (typeof query_string[pair[0]] === "undefined") {
query_string[pair[0]] = pair[1];
// If second entry with this name
} else if (typeof query_string[pair[0]] === "string") {
var arr = [ query_string[pair[0]], pair[1] ];
query_string[pair[0]] = arr;
// If third or later entry with this name
} else {
query_string[pair[0]].push(pair[1]);
}
}
return query_string;
};
How about this short functional approach?
function parseParams(str) {
return str.split('&').reduce(function (params, param) {
var paramSplit = param.split('=').map(function (value) {
return decodeURIComponent(value.replace(/\+/g, ' '));
});
params[paramSplit[0]] = paramSplit[1];
return params;
}, {});
}
Example:
parseParams("this=is&just=an&example") // Object {this: "is", just: "an", example: undefined}
My answer:
function(query){
var setValue = function(root, path, value){
if(path.length > 1){
var dir = path.shift();
if( typeof root[dir] == 'undefined' ){
root[dir] = path[0] == '' ? [] : {};
}
arguments.callee(root[dir], path, value);
}else{
if( root instanceof Array ){
root.push(value);
}else{
root[path] = value;
}
}
};
var nvp = query.split('&');
var data = {};
for( var i = 0 ; i < nvp.length ; i++ ){
var pair = nvp[i].split('=');
var name = decodeURIComponent(pair[0]);
var value = decodeURIComponent(pair[1]);
var path = name.match(/(^[^\[]+)(\[.*\]$)?/);
var first = path[1];
if(path[2]){
//case of 'array[level1]' || 'array[level1][level2]'
path = path[2].match(/(?=\[(.*)\]$)/)[1].split('][')
}else{
//case of 'name'
path = [];
}
path.unshift(first);
setValue(data, path, value);
}
return data;
}
I am using David Dorward's answer, and realized that it doesn't behave like PHP or Ruby on Rails how they parse the params:
1) a variable is only an array if it ends with [], such as ?choice[]=1&choice[]=12, not when it is ?a=1&a=2
2) when mulitple params exist with the same name, the later ones replaces the earlier ones, as on PHP servers (Ruby on Rails keep the first one and ignore the later ones), such as ?a=1&b=2&a=3
So modifying David's version, I have:
function QueryStringToHash(query) {
if (query == '') return null;
var hash = {};
var vars = query.split("&");
for (var i = 0; i < vars.length; i++) {
var pair = vars[i].split("=");
var k = decodeURIComponent(pair[0]);
var v = decodeURIComponent(pair[1]);
// If it is the first entry with this name
if (typeof hash[k] === "undefined") {
if (k.substr(k.length-2) != '[]') // not end with []. cannot use negative index as IE doesn't understand it
hash[k] = v;
else
hash[k.substr(0, k.length-2)] = [v];
// If subsequent entry with this name and not array
} else if (typeof hash[k] === "string") {
hash[k] = v; // replace it
// If subsequent entry with this name and is array
} else {
hash[k.substr(0, k.length-2)].push(v);
}
}
return hash;
};
which is tested fairly thoroughly.
I know this is an old thread, but maybe there is still some relevance in it?
Inspired by Jacky Li's good solution I tried a slight variation of my own with the objective to also be able to take care of arbitrary combinations of arrays and objects as input. I looked at how PHP would have done it and tried to get something "similar" going. Here is my code:
function getargs(str){
var ret={};
function build(urlnam,urlval,obj){ // extend the return object ...
var i,k,o=obj, x, rx=/\[([^\]]*)\]/g, idx=[urlnam.replace(rx,'')];
while (x=rx.exec(urlnam)) idx.push(x[1]);
while(true){
k=idx.shift();
if(k.trim()=='') {// key is empty: autoincremented index
if (o.constructor.name=='Array') k=o.length; // for Array
else if (o===obj ) {k=null} // for first level property name
else {k=-1; // for Object
for(i in o) if (+i>k) k=+i;
k++;
}
}
if(idx.length) {
// set up an array if the next key (idx[0]) appears to be
// numeric or empty, otherwise set up an object:
if (o[k]==null || typeof o[k]!='object') o[k]=isNaN(idx[0])?{}:[];
o=o[k]; // move on to the next level
}
else { // OK, time to store the urlval in its chosen place ...
// console.log('key',k,'val',urlval);
o[k]=urlval===""?null:urlval; break; // ... and leave the while loop.
}
}
return obj;
}
// ncnvt: is a flag that governs the conversion of
// numeric strings into numbers
var ncnvt=true,i,k,p,v,argarr=[],
ar=(str||window.location.search.substring(1)).split("&"),
l=ar.length;
for (i=0;i<l;i++) {if (ar[i]==="") continue;
p=ar[i].split("=");k=decodeURIComponent(p[0]);
v=p[1];v=(v!=null)?decodeURIComponent(v.replace(/\+/g,'%20')):'';
if (ncnvt && v.trim()>"" && !isNaN(v)) v-=0;
argarr.push([k,v]); // array: key-value-pairs of all arguments
}
for (i=0,l=argarr.length;i<l;i++) build(argarr[i][0],argarr[i][1],ret);
return ret;
}
If the function is called without the str-argument it will assume window.location.search.slice(1) as input.
Some examples:
['a=1&a=2', // 1
'x[y][0][z][]=1', // 2
'hello=[%22world%22]&world=hello', // 3
'a=1&a=2&&b&c=3&d=&=e&', // 4
'fld[2][]=2&fld[][]=3&fld[3][]=4&fld[]=bb&fld[]=cc', // 5
$.param({a:[[1,2],[3,4],{aa:'one',bb:'two'},[5,6]]}), // 6
'a[]=hi&a[]=2&a[3][]=7&a[3][]=99&a[]=13',// 7
'a[x]=hi&a[]=2&a[3][]=7&a[3][]=99&a[]=13'// 8
].map(function(v){return JSON.stringify(getargs(v));}).join('\n')
results in
{"a":2} // 1
{"x":{"y":[{"z":[1]}]}} // 2
{"hello":"[\"world\"]","world":"hello"} // 3
{"a":2,"b":null,"c":3,"d":null,"null":"e"} // 4 = { a: 2, b: null, c: 3, d: null, null: "e" }
{"fld":[null,null,[2],[3,4],"bb","cc"]} // 5
{"a":[[1,2],[3,4],{"aa":"one","bb":"two"},[5,6]]} // 6
{"a":["hi",2,null,[7,99],13]} // 7
{"a":{"0":2,"3":[7,99],"4":13,"x":"hi"}} // 8
Whereas Jacky Li's solution would produce the outer container for a as a plain object
{a:{"0":["1","2"],"1":["3","4"],"2":["5","6"]}} // 6: JackyLi's output
getargs() looks at the first given index for any level to determine whether this level will be an object (non-numeric index) or an array (numeric or empty), thus resulting in the output as shown in the listing bove (no. 6).
If the current object is an array then nulls get inserted wherever necessary to represent empty positions. Arrays are always consecutively numbered and 0-based).
Note, that in the example no. 8 the "autoincrement" for empty indices still works, even though we are dealing with an object now and not an array.
As far as I have tested it, my getargs() behaves pretty much identically to Chriss Roger's great jQuery $.deparam() plugin mentioned in the accepted answer. The main difference is that getargs runs without jQuery and that it does autoincrement in objects while $.deparam() will not do that:
JSON.stringify($.deparam('a[x]=hi&a[]=2&a[3][]=7&a[3][]=99&a[]=13').a);
results in
{"3":["7","99"],"x":"hi","undefined":"13"}
In $.deparam() the index [] is interpreted as an undefined instead of an autoincremented numerical index.
Here's how you could create a new jQuery function:
jQuery.unparam = function (value) {
var
// Object that holds names => values.
params = {},
// Get query string pieces (separated by &)
pieces = value.split('&'),
// Temporary variables used in loop.
pair, i, l;
// Loop through query string pieces and assign params.
for (i = 0, l = pieces.length; i < l; i++) {
pair = pieces[i].split('=', 2);
// Repeated parameters with the same name are overwritten. Parameters
// with no value get set to boolean true.
params[decodeURIComponent(pair[0])] = (pair.length == 2 ?
decodeURIComponent(pair[1].replace(/\+/g, ' ')) : true);
}
return params;
};
Thanks to him http://james.padolsey.com/javascript/parsing-urls-with-the-dom/
Pretty easy :D
function params_unserialize(p){
var ret = {},
seg = p.replace(/^\?/,'').split('&'),
len = seg.length, i = 0, s;
for (;i<len;i++) {
if (!seg[i]) { continue; }
s = seg[i].split('=');
ret[s[0]] = s[1];
}
return ret;}
This is really old question, but as i have coming - other people may coming to this post, and i want to a bit refresh this theme. Today no need to make custom solutions - there is URLSearchParams interface.
var paramsString = "q=URLUtils.searchParams&topic=api";
var searchParams = new URLSearchParams(paramsString);
//Iterate the search parameters.
for (let p of searchParams) {
console.log(p);
}
The only one limitation i know - this feature not supported in IE / Edge.
Here's my JavaScript implementation which I use in a server-side JScript ASP Classic page (demo):
// Transforms a query string in the form x[y][0][z][]=1 into {x:{y:[{z:[1]}]}}
function parseJQueryParams(p) {
var params = {};
var pairs = p.split('&');
for (var i=0; i<pairs.length; i++) {
var pair = pairs[i].split('=');
var indices = [];
var name = decodeURIComponent(pair[0]),
value = decodeURIComponent(pair[1]);
var name = name.replace(/\[([^\]]*)\]/g,
function(k, idx) { indices.push(idx); return ""; });
indices.unshift(name);
var o = params;
for (var j=0; j<indices.length-1; j++) {
var idx = indices[j];
var nextIdx = indices[j+1];
if (!o[idx]) {
if ((nextIdx == "") || (/^[0-9]+$/.test(nextIdx)))
o[idx] = [];
else
o[idx] = {};
}
o = o[idx];
}
idx = indices[indices.length-1];
if (idx == "") {
o.push(value);
}
else {
o[idx] = value;
}
}
return params;
}
I came up with this solution, which behaves like the .Net function HttpUtility.ParseQueryString.
In the result, the query string parameters are store in properties as lists of values, so that qsObj["param"] will be the same as calling GetValues("param") in .Net.
I hope you like it. JQuery not required.
var parseQueryString = function (querystring) {
var qsObj = new Object();
if (querystring) {
var parts = querystring.replace(/\?/, "").split("&");
var up = function (k, v) {
var a = qsObj[k];
if (typeof a == "undefined") {
qsObj[k] = [v];
}
else if (a instanceof Array) {
a.push(v);
}
};
for (var i in parts) {
var part = parts[i];
var kv = part.split('=');
if (kv.length == 1) {
var v = decodeURIComponent(kv[0] || "");
up(null, v);
}
else if (kv.length > 1) {
var k = decodeURIComponent(kv[0] || "");
var v = decodeURIComponent(kv[1] || "");
up(k, v);
}
}
}
return qsObj;
};
Here is how to use it:
var qsObj = parseQueryString("a=1&a=2&&b&c=3&d=&=e&");
To preview the result in the console juste type in:
JSON.stringify(qsObj)
Output:
"{"a":["1","2"],"null":["","b",""],"c":["3"],"d":[""],"":["e"]}"
There's a beautiful one-liner over at CSS-Tricks (original source from Nicholas Ortenzio):
function getQueryParameters(str) {
return (str || document.location.search).replace(/(^\?)/,'').split("&").map(function(n){return n = n.split("="),this[n[0]] = n[1],this}.bind({}))[0];
}
The really clever part is how it uses the anonymous function's this object, adding a key/value pair for each of the queries in the string. That said, there's some room for improvement. I've modified it a bit below, with the following changes:
Added handling of empty strings and non-string input.
Handled URI-encoded strings (%40->#, etc).
Removed the default use of document.location.search when the input was empty.
Changed the name, made it more readable, added comments.
function deparam(str) {
// Uses an empty 'this' to build up the results internally
function splitQuery(query) {
query = query.split('=').map(decodeURIComponent);
this[query[0]] = query[1];
return this;
}
// Catch bad input
if (!str || !(typeof str === 'string' || str instanceof String))
return {};
// Split the string, run splitQuery on each piece, and return 'this'
var queries = str.replace(/(^\?)/,'').split('&');
return queries.map(splitQuery.bind({}))[0];
}
use this :
// convert query string to json object
var queryString = "cat=3&sort=1&page=1";
queryString
.split("&")
.forEach((item) => {
const prop = item.split("=");
filter[prop[0]] = prop[1];
});
console.log(queryString);
This is my version in Coffeescript.
Also works for url like
http://localhost:4567/index.html?hello=[%22world%22]&world=hello#/home
getQueryString: (url)->
return null if typeof url isnt 'string' or url.indexOf("http") is -1
split = url.split "?"
return null if split.length < 2
path = split[1]
hash_pos = path.indexOf "#"
path = path[0...hash_pos] if hash_pos isnt -1
data = path.split "&"
ret = {}
for d in data
[name, val] = d.split "="
name = decodeURIComponent name
val = decodeURIComponent val
try
ret[name] = JSON.parse val
catch error
ret[name] = val
return ret
Here's a simple & compact one if you only want to quickly get the parameters from a GET request:
function httpGet() {
var a={},b,i,q=location.search.replace(/^\?/,"").split(/\&/);
for(i in q) if(q[i]) {b=q[i].split("=");if(b[0]) a[b[0]]=
decodeURIComponent(b[1]).replace(/\+/g," ");} return a;
}
It converts
something?aa=1&bb=2&cc=3
into an object like
{aa:1,bb:2,cc:3}
Creates a serialized representation of an array or object (can be used as URL query string for AJAX requests).
<button id='param'>GET</button>
<div id="show"></div>
<script>
$('#param').click(function () {
var personObj = new Object();
personObj.firstname = "vishal"
personObj.lastname = "pambhar";
document.getElementById('show').innerHTML=$.param(`personObj`));
});
</script>
output:firstname=vishal&lastname=pambhar
answers could use a bit of jQuery elegance:
(function($) {
var re = /([^&=]+)=?([^&]*)/g;
var decodeRE = /\+/g; // Regex for replacing addition symbol with a space
var decode = function (str) {return decodeURIComponent( str.replace(decodeRE, " ") );};
$.parseParams = function(query) {
var params = {}, e;
while ( e = re.exec(query) ) {
var k = decode( e[1] ), v = decode( e[2] );
if (k.substring(k.length - 2) === '[]') {
k = k.substring(0, k.length - 2);
(params[k] || (params[k] = [])).push(v);
}
else params[k] = v;
}
return params;
};
})(jQuery);
fork at https://gist.github.com/956897
You can use the function .serializeArray() (Link) of jQuery itself. This function returns an array of key-value pair. Result example:
[
{ name: "id", value: "1" },
{ name: "version", value: "100" }
]

Categories