如何确定变量是字符串还是JavaScript中的其他变量?


当前回答

表演

今天2020.09.17我在Chrome v85、Safari v13.1.2和Firefox v80上对MacOs HighSierra 10.13.6进行了测试,以确定所选的解决方案。

后果

对于所有浏览器(以及两个测试用例)

解决方案类型||instanceof(A,I)和x===x+''(H)是快速/最快的解决方案_.isString(lodash-lib)是中等/快速的解决方案B和K是最慢的

更新:2020.11.28我更新了x=123 Chrome列的结果-对于解决方案I,之前可能有一个错误值(=69M太低)-我使用Chrome 86.0重复测试。

细节

我为解决方案执行2个测试用例A.BCDEFGH我JKL

当变量为字符串时,可以在此处运行当变量不是字符串时-可以在此处运行

下面的代码片段显示了解决方案之间的差异

// https://stackoverflow.com/a/9436948/860099函数A(x){return(typeof x==“string”)||(x instanceof string)}// https://stackoverflow.com/a/17772086/860099函数B(x){return Object.pr原型.toString.call(x)==“[对象字符串]”}// https://stackoverflow.com/a/20958909/860099函数C(x){return _.isString(x);}// https://stackoverflow.com/a/20958909/860099函数D(x){return$.type(x)==“string”;}// https://stackoverflow.com/a/16215800/860099函数E(x){返回x?。constructor==字符串;}// https://stackoverflow.com/a/42493631/860099函数F(x){返回x?。charAt!=无效的}// https://stackoverflow.com/a/57443488/860099函数G(x){return字符串(x)==x}// https://stackoverflow.com/a/19057360/860099函数H(x){返回x===x+''}// https://stackoverflow.com/a/4059166/860099函数I(x){返回类型x==“string”}// https://stackoverflow.com/a/28722301/860099函数J(x){返回x===x?。到字符串()}// https://stackoverflow.com/a/58892465/860099函数K(x){返回x&&typeof x.valueOf()==“string”}// https://stackoverflow.com/a/9436948/860099函数L(x){return x字符串实例}// ------------------//演示文稿// ------------------console.log('不同输入的解决方案结果\n\n');console.log(“'abc'Str‘‘‘‘1‘‘0‘1 0{}〔〕true false null undef”);let tests=['abc',new String(“abc”),'','','1','0',1,0,{},[],true,false,null,undefined];[A,B,C,D,E,F,G,H,I,J,K,L]映射(F=>{控制台日志(`${f.name}`+测试.map(v=>(1*!!f(v))).join``)})<script src=“https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js“></script><script src=“https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.20/lodash.min.js“integrity=”sha512-90vH1Z83AJY9DmlWa8WkjkV79yfS2n2Oxhsi2dZbIv0nC4E6m5AbH8Nh156kkM7JePmqD6tcZsfad1ueoaovww==“crossrorigin=”匿名“></script>此shippet只显示性能测试中使用的函数,而不执行测试本身!

下面是铬的示例结果

其他回答

isString()使用可选链接和最新标准检查传递的参数是否为字符串:

const isString = (value) => { 
    return value?.constructor === String;
}

我不确定你的意思是知道它是一个类型字符串而不管它的内容,还是它的内容是一个数字或字符串而不管其类型。所以要知道它的类型是否是字符串,这已经得到了答案。但要根据它的内容知道它是字符串还是数字,我会使用这个:

function isNumber(item) {
    return (parseInt(item) + '') === item;
}

例如:

isNumber(123);   //true
isNumber('123'); //true
isNumber('123a');//false
isNumber('');    //false

这对我来说已经足够好了。

警告:这不是一个完美的解决方案。请看我帖子的底部。

Object.prototype.isString = function() { return false; };
String.prototype.isString = function() { return true; };

var isString = function(a) {
  return (a !== null) && (a !== undefined) && a.isString();
};

你可以像下面这样使用。

//return false
isString(null);
isString(void 0);
isString(-123);
isString(0);
isString(true);
isString(false);
isString([]);
isString({});
isString(function() {});
isString(0/0);

//return true
isString("");
isString(new String("ABC"));

警告:在以下情况下,此操作不正确:

//this is not a string
var obj = {
    //but returns true lol
    isString: function(){ return true; }
}

isString(obj) //should be false, but true

我发现这种简单的技术对字符串的类型检查很有用-

String(x) === x // true, if x is a string
                // false in every other case

常量测试=x=>控制台断言(字符串(x)==x,`不是字符串:${x}`)测试(“某些字符串”)测试(123)//断言失败测试(0)//断言失败测试(/some regex/)//断言失败测试([5],6])//断言失败测试({a:1})//断言失败测试(x=>x+1)//断言失败

同样的技术也适用于Number-

Number(x) === x // true, if x is a number
                // false in every other case

常量测试=x=>控制台断言(数量(x)==x,`不是数字:${x}`)test(“some string”)//断言失败测试(123)测试(0)测试(/some regex/)//断言失败测试([5],6])//断言失败测试({a:1})//断言失败测试(x=>x+1)//断言失败

对于RegExp-

RegExp(x) === x // true, if x is a regexp
                // false in every other case

常量测试=x=>控制台断言(RegExp(x)==x,`不是正则表达式:${x}`)test(“some string”)//断言失败测试(123)//断言失败测试(0)//断言失败测试(/some regex/)测试([5],6])//断言失败测试({a:1})//断言失败测试(x=>x+1)//断言失败

与对象相同-

Object(x) === x // true, if x is an object
                // false in every other case

NB、正则表达式、数组和函数也被视为对象。

常量测试=x=>控制台断言(对象(x)==x,`不是对象:${x}`)test(“some string”)//断言失败测试(123)//断言失败测试(0)//断言失败测试(/some regex/)测试([5,6])测试({a:1})测试(x=>x+1)

但是,检查Array有点不同-

Array.isArray(x) === x // true, if x is an array
                       // false in every other case

常量测试=x=>控制台断言(Array.isArray(x),`不是数组:${x}`)test(“some string”)//断言失败测试(123)//断言失败测试(0)//断言失败测试(/some regex/)//断言失败测试([5,6])测试({a:1})//断言失败测试(x=>x+1)//断言失败

但是,此技术不适用于函数-

Function(x) === x // always false

对于@Faither-

const fmt=JSON.stringify函数测试1(){常量a=“1”常量b=1console.log(`编号(${fmt(a)})==${mt(b)}`,编号(a)==b)//true}函数测试2(){常量a=“1”常量b=1console.log(`Number.isInteger(${fmt(a)})`,Number.isInteger(a))//falseconsole.log(`Number.isInteger(${fmt(b)})`,Number.isInteger(b))//true}函数测试3(){name=1//全局名称将始终为字符串console.log(fmt(名称))//“1”console.log(`字符串(${fmt(名称)})==${mt(名称)}`,字符串(名称)==名称)//true}函数测试4(){常量名称=1//本地名称console.log(fmt(名称))//1console.log(`字符串(${fmt(名称)})==${mt(名称)}`,字符串(名称)==名称)//false}测试1();test2();测试3();测试4()

var a = new String('')
var b = ''
var c = []

function isString(x) {
  return x !== null && x !== undefined && x.constructor === String
}

console.log(isString(a))
console.log(isString(b))
console.log(isString(c))