今回は動作確認用にgetCloneという関数をグローバル領域に作成しましたが、用途・目的としてはsetProp以外から呼び出すことは無さそうな気がするのでsetPropからしか呼べない(グローバル領域を汚さない)ようにしようか検討中。。
以下ソース
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<job> | |
<script> | |
getClone=function(){ | |
var gt=function(obj){return typeof(obj)} | |
var gc=function(obj){return obj.constructor} | |
var objT={} | |
objT[gt('')] = objT[gt(0)] = objT[gt(true)] = objT[gt(objT.und)] = true | |
var objC={} | |
objC[gc({})] = function(obj,swSub){return setProp({}, obj, swSub)} | |
objC[gc([])] = function(obj,swSub){return setProp([], obj, swSub)} | |
objC[gc(/1/)] = function(obj){var re; eval('re = '+obj); return re} | |
objC[gc(new Date())] = function(obj){return new Date(obj+'')} | |
objC[gc(gc)] = function(obj,swSub){var f; eval('f = '+obj); return setProp(f, obj, swSub)} | |
return function(obj, swSub){ return (objT[gt(obj)] || obj===null) ? obj : objC[gc(obj)](obj, swSub) } | |
}() | |
forIn = function(obj,fun){var name,res; for(name in obj){if(res=fun(name, obj[name])){return res}}} | |
setProp=function(objTarget, objProp, swSub, swValue){ | |
var funChildsCheck=function(){return true} | |
var arrT=[], arrP=[], 階層=-1, arrC=[].constructor | |
var fun=function(n,v){ | |
if(swSub && forIn(v,funChildsCheck)){ | |
fun0(arrT[階層][n] || (arrT[階層][n]=getClone(v)), v) | |
return | |
} | |
if(swValue && !v){return} | |
arrT[階層][n] = v | |
} | |
var fun0=function(objT, objP){ | |
arrT.push(objT) | |
arrP.push(objP) | |
階層++ | |
forIn(objP, fun) | |
階層-- | |
arrT.pop() | |
arrP.pop() | |
} | |
fun0(objTarget, objProp) | |
return objTarget | |
} | |
WScript.Echo(typeof(true)+'\n\n'+getClone(true)) | |
obj0 = {a:1, b:2} | |
obj1 = getClone(obj0) | |
obj1.a = 3 | |
// obj0.a:1 | |
WScript.Echo('obj0.a:'+obj0.a) | |
// obj1.a:3 | |
WScript.Echo('obj1.a:'+obj1.a) | |
arr0 = [1,2,3] | |
arr1 = getClone(arr0) | |
// arr1.length:3 | |
WScript.Echo('arr1.length:'+arr1.length) | |
dat0 = new Date('2016/12/25 00:11:22') | |
dat1 = getClone(dat0) | |
// dat1:Sun Dec 25 00:11:22 UTC+0900 2016 | |
WScript.Echo('dat1:'+dat1) | |
fun0 = function(){ WScript.Echo(arguments.callee.num) } | |
fun0.num = 123 | |
fun1 = getClone(fun0) | |
fun1.num = 456 | |
// 123 | |
fun0() | |
// 456 | |
fun1() | |
if(0){ | |
var un={} | |
// error un.a.constructorはNullまたはオブジェクトではありません | |
// WScript.Echo(un.a.constructor) | |
WScript.Echo(null) | |
// null.constructorはNullまたはオブジェクトではありません | |
// WScript.Echo(null.constructor) | |
// boolean | |
WScript.Echo(typeof(true)) | |
// object | |
WScript.Echo(typeof(null)) | |
// undefined | |
WScript.Echo(typeof(un.a)) | |
// string | |
WScript.Echo(typeof('')) | |
// string | |
WScript.Echo(typeof('str')) | |
// number | |
WScript.Echo(typeof(0)) | |
// /1/g | |
WScript.Echo(/1/g) | |
// Wed Feb 15 16:45:23 UTC+0900 2017 | |
var d=new Date() | |
WScript.Echo([d, new Date(d+'')].join('\n')) | |
} | |
</script> | |
</job> |
Mathが対象になるケースはないだろう、とかDate、RegExpオブジェクトにプロパティを追加することはないだろう、という予想で上記のようにしていますが、もし必要ならobjC[gc(/1/)]などの中でもsetPropを呼ぶように変更すればOK。
0 件のコメント:
コメントを投稿