यदि मान एक फ़ंक्शन है तो परीक्षण करना


88

मुझे यह परीक्षण करने की आवश्यकता है कि क्या किसी फॉर्म का मूल्य onsubmitएक फ़ंक्शन है। प्रारूप आमतौर पर है onsubmit="return valid();"। क्या यह बताने का कोई तरीका है कि क्या यह एक फ़ंक्शन है, और यदि यह कॉल करने योग्य है? टाइपोफ़ का उपयोग करना केवल यह बताता है कि यह एक स्ट्रिंग है, जो मुझे बहुत मदद नहीं करता है।

संपादित करें : निश्चित रूप से, मैं समझता हूं कि "वापसी वैध ();" एक तार है। मैंने इसे replace"मान्य ();", और यहां तक ​​कि "मान्य ()" के लिए निर्धारित किया है। मैं जानना चाहता हूं कि क्या उनमें से कोई एक फ़ंक्शन है।

संपादित करें : यहाँ कुछ कोड है, जो मेरी समस्या को समझाने में मदद कर सकते हैं:

$("a.button").parents("form").submit(function() {
    var submit_function = $("a.button").parents("form").attr("onsubmit");
    if ( submit_function && typeof( submit_function.replace(/return /,"") ) == 'function' ) {
        return eval(submit_function.replace(/return /,""));
    } else {
        alert("onSubmit is not a function.\n\nIs the script included?"); return false;
    }
} );

EDIT 2 : यहां नया कोड है। ऐसा लगता है कि मुझे अभी भी एक इवैल का उपयोग करना है, क्योंकि कॉलिंग फॉर्म.सुमिट () मौजूदा ऑनूबमिट्स को फायर नहीं करता है।

var formObj = $("a.button").parents("form");
formObj.submit(function() {
    if ( formObj[0].onsubmit && typeof( formObj.onsubmit ) == 'function' ) {
        return eval(formObj.attr("onsubmit").replace(/return /,""));
    } else {
        alert("onSubmit is not a function.\n\nIs the script included?");
        return false;
    }
} );

संभवत: यह बेहतर करने के लिए सुझाव?

जवाबों:


85

मैं एंकर लिंक के साथ सबमिट बटन की जगह ले रहा हूं। चूंकि कॉलिंग फॉर्म.सुमिट () ऑनसुमिट का सक्रिय नहीं करता है, मैं इसे ढूंढ रहा हूं, और इसे खुद से बाहर निकालना चाहता हूं। लेकिन मैं जाँच करना चाहूँगा कि क्या फ़ंक्शन केवल eval () आईएनजी से पहले मौजूद है। - gms8994

<script type="text/javascript">
function onsubmitHandler() {
    alert('running onsubmit handler');
    return true;
}
function testOnsubmitAndSubmit(f) {
    if (typeof f.onsubmit === 'function') {
        // onsubmit is executable, test the return value
        if (f.onsubmit()) {
            // onsubmit returns true, submit the form
            f.submit();
        }
    }
}
</script>

<form name="theForm" onsubmit="return onsubmitHandler();">
<a href="#" onclick="
    testOnsubmitAndSubmit(document.forms['theForm']);
    return false;
"></a>
</form>

संपादित करें: फ़ंक्शन टेस्ट में अनुपलब्ध पैरामीटर f .OnsubmitAndSubmit

चाहे आप onsubmitHTML विशेषता असाइन करें या इसे जावास्क्रिप्ट में निर्दिष्ट करें, ऊपर दिए बिना काम करना चाहिए :

document.forms['theForm'].onsubmit = onsubmitHandler;

1
f.onsubmit में f कहाँ से आता है?
आर्ट

fएक उदाहरण है। आप इसे एक तर्क के रूप में testOnsubmitAndSubmit फ़ंक्शन में पास करते हैं। (मुझे पता है कि यह सवाल बहुत पुराना है, लेकिन शायद मेरा जवाब किसी को कुछ समय बचा लेगा :))
जीरो

63

प्रयत्न

if (this.onsubmit instanceof Function) {
    // do stuff;
}

7
यह सिर्फ एक नमूना है। आप इसे बटन पर बदल सकते हैं। इंसुबिमिट इंस्टोफ फंक्शन
आर्टिम्बेंट

13

आप बस typeofऑपरेटर को शॉर्ट के लिए एक टर्नरी ऑपरेटर के साथ उपयोग कर सकते हैं :

onsubmit="return typeof valid =='function' ? valid() : true;"

यदि यह एक फ़ंक्शन है तो हम इसे कॉल करते हैं और इसे वापस लौटाते हैं, अन्यथा वापस आ जाते हैं true

संपादित करें:

मुझे पूरा यकीन नहीं है कि आप वास्तव में क्या करना चाहते हैं, लेकिन मैं यह बताने की कोशिश करूंगा कि क्या हो रहा है।

जब आप अपने onsubmitकोड को अपने HTML में घोषित करते हैं , तो यह एक फ़ंक्शन में बदल जाता है और इस प्रकार जावास्क्रिप्ट "दुनिया" से इसका कॉल करने योग्य होता है। इसका मतलब है कि वे दो विधियाँ समतुल्य हैं:

HTML: <form onsubmit="return valid();" />
JavaScript: myForm.onsubmit = function() { return valid(); };

ये दोनों कार्य होंगे और दोनों ही कॉल करने योग्य होंगे। आप typeofऑपरेटर का उपयोग करने वालों में से किसी का भी परीक्षण कर सकते हैं, जिसे समान परिणाम प्राप्त करना चाहिए:"function"

अब यदि आप जावास्क्रिप्ट के माध्यम से "ऑनसाइट" संपत्ति के लिए एक स्ट्रिंग असाइन करते हैं, तो यह एक स्ट्रिंग रहेगा, इसलिए कॉल करने योग्य नहीं है। ध्यान दें कि यदि आप typeofइसके विरुद्ध ऑपरेटर को लागू करते हैं , तो आपको "string"इसके बदले मिलेगा "function"

मुझे उम्मीद है कि यह कुछ चीजों को स्पष्ट कर सकता है। फिर, यदि आप जानना चाहते हैं कि क्या ऐसी संपत्ति (या मामले के लिए कोई पहचानकर्ता) एक फ़ंक्शन और कॉल करने योग्य है, तोtypeof ऑपरेटर को चाल करना चाहिए। हालांकि मुझे यकीन नहीं है कि यह कई फ्रेम में ठीक से काम करता है।

चियर्स


हालाँकि, मुझे ऑनबसमिट के बाहर इसका परीक्षण करने की आवश्यकता है।
Glen Solsberry

5

आप कौन सा ब्राउज़र उपयोग कर रहे हैं?

alert(typeof document.getElementById('myform').onsubmit);

यह मुझे functionIE7 और फायरफॉक्स में " " देता है ।


भले ही आपका ऑनसुबमिट "रिटर्न वैलिड ()?"
बजे ग्लेन सोल्स्बरी

1
हाँ - मत भूलो, तुम एक समारोह के बाहर "वापसी" नहीं कर सकते।
ग्रेग

form.onsubmit हमेशा एक फ़ंक्शन होगा जब तक कि इसे HTML विशेषता के रूप में परिभाषित किया जाता है। मेरा जवाब देखिए।
इओनु

4

उदाहरण के रूप में एक स्ट्रिंग आधारित चर का उपयोग instanceof Function करना और उपयोग करना आप फ़ंक्शन को पंजीकृत करते हैं.. चर की जाँच करें ... चर की जाँच करें फ़ंक्शन का नाम है ... पूर्व-प्रक्रिया करें ... फ़ंक्शन को नए संस्करण में असाइन करें ... फिर फ़ंक्शन को कॉल करें।

function callMe(){
   alert('You rang?');
}

var value = 'callMe';

if (window[value] instanceof Function) { 
    // do pre-process stuff
    // FYI the function has not actually been called yet
    console.log('callable function');
    //now call function
   var fn = window[value];
   fn();
}

2
आपको वास्तव में उस fn वैरिएबल की आवश्यकता नहीं है, आप बस विंडो का उपयोग कर सकते हैं [value] ();
लाजोस मेस्सरोस

1
हाँ, मुझे पता है लेकिन मुझे यह भी पता है कि आमतौर पर एक लंबे प्रारूप में समझना आसान होता है और जैसा कि यह मुख्य रूप से आपके इनपुट को सीखने के लिए एक साइट है, किसी भी मामले में मूल्यवान है @LajosMeszaros
CrandellWS

3

सुनिश्चित करें कि आप वास्तविक फ़ंक्शन पर टाइपोफ़ कॉल कर रहे हैं, न कि एक स्ट्रिंग शाब्दिक:

function x() { 
    console.log("hi"); 
}

typeof "x"; // returns "string"

typeof x; // returns "function"

3

आप अपनी आवश्यकताओं के अनुरूप इस तकनीक को संशोधित करने का प्रयास कर सकते हैं:

 function isFunction() {
   var functionName = window.prompt('Function name: ');
   var isDefined = eval('(typeof ' + functionName + '==\'function\');');
   if (isDefined)
     eval(functionName + '();');
   else
     alert('Function ' + functionName + ' does not exist');
 }
 function anotherFunction() {
   alert('message from another function.');
 }

2

form.onsubmit हमेशा एक फ़ंक्शन होगा जब HTML को तत्व तत्व के रूप में परिभाषित किया जाता है। यह एक HTML तत्व से जुड़ा हुआ कुछ प्रकार का अनाम फ़ंक्शन है, जिसमें यह सूचक उस FORM तत्व से जुड़ा होता है और जिसका एक पैरामीटर नाम भी होता हैevent सबमिट इवेंट के बारे में डेटा होता है।

इन परिस्थितियों में मुझे समझ नहीं आता है कि आपको टाइपोफ ऑपरेशन के परिणामस्वरूप स्ट्रिंग कैसे मिली। आपको अधिक विवरण, बेहतर कुछ कोड देना चाहिए।

संपादित करें (आपके दूसरे संपादन के जवाब के रूप में):

मेरा मानना ​​है कि HTML विशेषता से जुड़ा हैंडलर उपरोक्त कोड की परवाह किए बिना निष्पादित करेगा। इसके अलावा, आप इसे किसी भी तरह से रोकने की कोशिश कर सकते हैं, लेकिन, ऐसा प्रतीत होता है कि एफएफ 3, आईई 8, क्रोम 2 और ओपेरा 9 HTML विशेषता हैंडलर को पहले स्थान पर निष्पादित कर रहे हैं और फिर एक संलग्न है (मैंने jQuery के साथ परीक्षण नहीं किया था हालांकि, लेकिन addEventListener और संलग्नक के साथ)। तो ... क्या आप वास्तव में पूरा करने की कोशिश कर रहे हैं?

वैसे, आपका कोड काम नहीं कर रहा है क्योंकि आपकी नियमित अभिव्यक्ति स्ट्रिंग को "वैध (") निकाल देगी, जो निश्चित रूप से एक फ़ंक्शन नहीं है।


2

यदि यह एक तार है, तो आप मान सकते हैं / यह हमेशा फॉर्म का है

return SomeFunction(arguments);

फ़ंक्शन नाम के लिए पार्स, और फिर देखें कि क्या फ़ंक्शन का उपयोग करके परिभाषित किया गया है

if (window[functionName]) { 
    // do stuff
}

मैं इस रिज़ॉल्यूशन को जोड़ने वाला था ... दस्तावेज़ / विंडो स्तर पर फ़ंक्शन को पंजीकृत करने के लिए बस याद रखें
CrandellWS

1

खैर, "return valid();" है एक स्ट्रिंग है, ताकि के सही करें।

यदि आप जांचना चाहते हैं कि क्या इसकी जगह कोई फ़ंक्शन जुड़ा हुआ है, तो आप यह कोशिश कर सकते हैं:

formId.onsubmit = function (){ /* */ }

if(typeof formId.onsubmit == "function"){
  alert("it's a function!");
}

1

मुझे लगता है कि भ्रम का स्रोत नोड की विशेषता और संबंधित संपत्ति के बीच का अंतर है

आप उपयोग कर रहे हैं:

$("a.button").parents("form").attr("onsubmit")

आप सीधे onsubmit विशेषता के मूल्य (जो एक स्ट्रिंग होना चाहिए) को पढ़ रहे हैं । इसके बजाय, आपको नोड की onsubmit संपत्ति का उपयोग करना चाहिए :

$("a.button").parents("form").prop("onsubmit")

यहाँ एक त्वरित परीक्षण है:

<form id="form1" action="foo1.htm" onsubmit="return valid()"></form>
<script>
window.onload = function () {
    var form1 = document.getElementById("form1");

    function log(s) {
        document.write("<div>" + s + "</div>");
    }

    function info(v) {
        return "(" + typeof v + ") " + v;
    }

    log("form1 onsubmit property: " + info(form1.onsubmit));
    log("form1 onsubmit attribute: " + info(form1.getAttribute("onsubmit")));
};
</script> 

यह प्रदान करता है:

form1 ऑनसाइट संपत्ति: (फ़ंक्शन) फ़ंक्शन ऑनूबमिट (ईवेंट) {रिटर्न वैध (); }
फ़ॉर्म 1 ऑनसुमिट विशेषता: (स्ट्रिंग) वैध वापसी ()


1

नहीं है typeof xxx === 'function'सबसे अच्छा और सबसे तेजी से?

मैंने विच में एक बेंच बनाया था जिसे आप इंस्टॉफ़ और _underscore की तुलना में आज़मा सकते हैं

  1. यह सिर्फ instof (क्रोम का उपयोग करके) की तुलना में तेज़ लगता है
  2. यदि चर को परिभाषित नहीं किया गया है, तो यह एक त्रुटि नहीं है

यहाँ एक बेंच: https://jsbench.me/qnkf076cqb/1


0

आप हमेशा जावास्क्रिप्ट ब्लॉग जैसे क्रिस वेस्ट पर टाइपऑफ कार्यों में से एक का उपयोग कर सकते हैं । typeOf()कार्य के लिए निम्नलिखित जैसे परिभाषा का उपयोग करना काम करेगा:

function typeOf(o){return {}.toString.call(o).slice(8,-1)}

यह फ़ंक्शन (जिसे वैश्विक नामस्थान में घोषित किया गया है, इस तरह इस्तेमाल किया जा सकता है:

alert("onsubmit is a " + typeOf(elem.onsubmit));

यदि यह एक फ़ंक्शन है, तो "फ़ंक्शन" वापस किया जाएगा। यदि यह एक स्ट्रिंग है, तो "स्ट्रिंग" वापस आ जाएगी। अन्य संभावित मूल्य यहां दिखाए गए हैं


0
// This should be a function, because in certain JavaScript engines (V8, for
// example, try block kills many optimizations).
function isFunction(func) {
    // For some reason, function constructor doesn't accept anonymous functions.
    // Also, this check finds callable objects that aren't function (such as,
    // regular expressions in old WebKit versions), as according to EcmaScript
    // specification, any callable object should have typeof set to function.
    if (typeof func === 'function')
        return true

    // If the function isn't a string, it's probably good idea to return false,
    // as eval cannot process values that aren't strings.
    if (typeof func !== 'string')
        return false

    // So, the value is a string. Try creating a function, in order to detect
    // syntax error.
    try {
        // Create a function with string func, in order to detect whatever it's
        // an actual function. Unlike examples with eval, it should be actually
        // safe to use with any string (provided you don't call returned value).
        Function(func)
        return true
    }
    catch (e) {
        // While usually only SyntaxError could be thrown (unless somebody
        // modified definition of something used in this function, like
        // SyntaxError or Function, it's better to prepare for unexpected.
        if (!(e instanceof SyntaxError)) {
            throw e
        }

        return false
    }
}

-3

इस तरह एक साधारण जाँच आपको बताएगी कि क्या यह मौजूद है / परिभाषित:

if (this.onsubmit)
{
  // do stuff;
}

6
यह काम नहीं करेगा। अगर ऑनसाइड के रूप में अच्छी तरह से एक गैर-स्ट्रिंग स्ट्रिंग है, तो TRUE पर जोर देगा।
एसईबी

1
परीक्षण का एक भयानक तरीका अगर कुछ एक फ़ंक्शन है - जैसा कि संकेत दिया गया है, और स्पष्ट होने के लिए: कुछ भी "सत्य" इस कोड को "सामान करने" के लिए कारण होगा और जो अपेक्षित नहीं है वह हो सकता है। यदि यह .onsubmit 5 या "hello" के मान पर सेट किया गया था या जावास्क्रिप्ट में कुछ और जो सत्य का मूल्यांकन करता है, तो आपको अप्रत्याशित व्यवहार मिलने वाला है।
जेसन बंटिंग

प्रश्न का विषय पूछता है कि कैसे जांचा जाए कि कुछ मौजूद है या नहीं। यह सब मैं सुझा रहा था - कोई और अधिक, कोई कम नहीं।
कोन

वास्तव में नहीं - मूल पोस्ट में कहा गया है कि उसे "परीक्षण करने की आवश्यकता है कि क्या फॉर्म के ऑनसुबमिट का मूल्य एक फ़ंक्शन है।" आपकी स्थिति यह नहीं है कि यह है या नहीं। ऑनसुमिट एक क्यूटकॉन है, आपका परीक्षण बस पूछता है कि क्या यह नहीं है। ऑनसुमिट "सत्य" है
जेसन बंटिंग
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.