জাভাস্ক্রিপ্টে একটি কাস্টম কলব্যাক তৈরি করুন


322

আমার এখনকার কাজটি হ'ল আমার বর্তমান ফাংশনটির কার্যকারিতা শেষ হলে কলব্যাক ফাংশন সম্পাদন করা উচিত।

function LoadData() 
{
    alert('The data has been loaded');
    //Call my callback with parameters. For example,
    //callback(loadedData , currentObject);
}

এই ফাংশনের জন্য একজন গ্রাহক এরকম হওয়া উচিত:

object.LoadData(success);

function success(loadedData , currentObject) 
{
  //Todo: some action here 
}

আমি কীভাবে এটি বাস্তবায়ন করব?


3
object.LoadData(success)কল অবশ্যই সংজ্ঞায়িত হওয়ার পরে হওয়া উচিত function success। অন্যথায়, আপনি ফাংশন সংজ্ঞায়িত না বলে আপনাকে একটি ত্রুটি পাবেন।
জে ব্রুনি

উত্তর:


574

আসলে, আপনার কোডটি ঠিক তেমন কাজ করবে, কেবল আপনার কলব্যাকটিকে একটি আর্গুমেন্ট হিসাবে ঘোষণা করুন এবং আপনি যুক্তির নাম ব্যবহার করে সরাসরি কল করতে পারেন।

অধিকার

function doSomething(callback) {
    // ...

    // Call the callback
    callback('stuff', 'goes', 'here');
}

function foo(a, b, c) {
    // I'm the callback
    alert(a + " " + b + " " + c);
}

doSomething(foo);

এটি কল করবে doSomething, যা কল করবে foo, যা "জিনিস এখানে চলে যায়" সতর্ক করবে will

মনে রাখবেন যে ফাংশনটি কল করা এবং এর ফলাফলটি ( ) পাস করার পরিবর্তে ফাংশন রেফারেন্স ( foo) পাস করা খুব গুরুত্বপূর্ণ foo()। আপনার প্রশ্নে, আপনি এটি সঠিকভাবে করেন তবে এটি নির্দিষ্ট করে দেখানো ঠিক কারণ এটি একটি সাধারণ ত্রুটি।

আরও উন্নত জিনিস

কখনও কখনও আপনি কলব্যাক কল করতে চান যাতে এটির জন্য একটি নির্দিষ্ট মান দেখতে পাওয়া যায় this। আপনি সহজেই জাভাস্ক্রিপ্ট callফাংশন দিয়ে এটি করতে পারেন :

function Thing(name) {
    this.name = name;
}
Thing.prototype.doSomething = function(callback) {
    // Call our callback, but using our own instance as the context
    callback.call(this);
}

function foo() {
    alert(this.name);
}

var t = new Thing('Joe');
t.doSomething(foo);  // Alerts "Joe" via `foo`

আপনি যুক্তিগুলিও পাস করতে পারেন:

function Thing(name) {
    this.name = name;
}
Thing.prototype.doSomething = function(callback, salutation) {
    // Call our callback, but using our own instance as the context
    callback.call(this, salutation);
}

function foo(salutation) {
    alert(salutation + " " + this.name);
}

var t = new Thing('Joe');
t.doSomething(foo, 'Hi');  // Alerts "Hi Joe" via `foo`

কখনও কখনও আপনি ব্যক্তিগতভাবে না হয়ে অ্যারে হিসাবে কলব্যাক দিতে চান এমন আর্গুমেন্টগুলি পাস করার জন্য এটি দরকারী। আপনি এটি করতে ব্যবহার করতে পারেন apply:

function Thing(name) {
    this.name = name;
}
Thing.prototype.doSomething = function(callback) {
    // Call our callback, but using our own instance as the context
    callback.apply(this, ['Hi', 3, 2, 1]);
}

function foo(salutation, three, two, one) {
    alert(salutation + " " + this.name + " - " + three + " " + two + " " + one);
}

var t = new Thing('Joe');
t.doSomething(foo);  // Alerts "Hi Joe - 3 2 1" via `foo`

আমি জানি যে আপনি যে উদাহরণটি লিখেছেন তার মতো কোনও পরামিতি না থাকলে এটি কাজ করবে তবে আমি যখন পরামিতিগুলি দিয়ে কোনও ফাংশনটি পাস করার চেষ্টা করব তখন এটি একটি ব্যতিক্রম ছুঁড়ে দেয় এবং আমাকে ফাংশনটি সংজ্ঞায়িত করা হয় না
আমগাদ ফাহমি

@ টিটিএন: এটি আশ্চর্যজনক, কলব্যাকটিতে প্যারামিটারগুলি পাস করার বিষয়ে বিশেষ কিছু নেই। আপনি আপনার ফাংশনে যে কলব্যাক রেফারেন্সটি পাস করেন তা হ'ল অন্যগুলির মতো ফাংশন রেফারেন্স, আপনি এটি দিয়ে সমস্ত সাধারণ জিনিস করতে পারেন।
টিজে ক্রাউডার

4
যে সমস্ত উত্তর দিয়েছেন: আমি মনে করি টিটএনের সমস্যা হ'ল তিনি জানেন না যে কোনও ফাংশন কীভাবে কলব্যাকের মধ্যে যুক্তি প্রয়োজন যা কোনও যুক্তি পাস না করে পাস করতে পারেন। ভাবি setTimeout()। উত্তরটি হ'ল doSomething(function(){foo('this','should','work')})
কলব্যাকটি

কেউ টিটিএএনকে উপরের বিষয়টি নিয়ে একটি থ্রেডের দিকে (সম্ভবত এসও তে) নির্দেশ করেছেন, আমার অনুসন্ধান-ফু আজ দুর্বল।
slebetman

1
@ ওয়েবউম্যান - এটি আপনার ব্যবহারের ক্ষেত্রে নির্ভর করে। আপনি এটি আর্গুমেন্ট হিসাবে পাস করতে পারেন, বা এটি কোনও ধরণের সেটিংস / অপশন অবজেক্টে বা অন্য কয়েকটি বিকল্পের মধ্যে অন্তর্ভুক্ত করতে পারেন।
টিজে ক্রাউডার

77

কলব্যাক কার্যকর করার চেষ্টা করার আগে এটি একটি বাস্তব ফাংশন কিনা তা নিশ্চিত করা ভাল অনুশীলন:

if (callback && typeof(callback) === "function") {

  callback();
}

21
if(typeof callback == "function")একই ফলাফল হবে।
পুনর্গঠন

22
হ্যাঁ, তবে যদি কোনও কলব্যাক না থাকে তবে কেন এটি টাইপ-ইনং করে বিরক্ত করবেন? এটাই callback && ...
Theonlygusti


10
function loadData(callback) {

    //execute other requirement

    if(callback && typeof callback == "function"){
        callback();
   }
}

loadData(function(){

   //execute callback

});

6
আপনার কোডটি কী করে এবং কেন এটি সমস্যার সমাধান করবে সে সম্পর্কে আরও ব্যাখ্যা যুক্ত করতে আপনার পোস্টটি সম্পাদনা করার বিষয়টি বিবেচনা করুন। একটি উত্তর যা বেশিরভাগ সবে কোড থাকে (এমনকি এটি কাজ করে) সাধারণত ওপিকে তাদের সমস্যা বুঝতে সাহায্য করবে। তবে এক্ষেত্রে, এটি ইতিমধ্যে পোস্ট করা অত্যন্ত সম্মানিত উত্তরগুলির সাথে একটি খুব পুরানো প্রশ্ন, যখন আরও নতুন মনোযোগ সহ আরও নতুন প্রশ্ন আসতে পারে তখন এই উত্তর দেওয়ার পক্ষে আপনার পক্ষে উপযুক্ত হবে না।
সুপারবিসাইডম্যান

1
লোকেরা কী দেখতে চায় তার এটির পূর্বের এই প্রদর্শনীর উত্তরটি আমার পছন্দ হয়েছে।
Aft3rL1f3

5
   function callback(e){
      return e;
   }
    var MyClass = {
       method: function(args, callback){
          console.log(args);
          if(typeof callback == "function")
          callback();
       }    
    }

==============================================

MyClass.method("hello",function(){
    console.log("world !");
});

==============================================

ফলাফলটি হ'ল:

hello world !

4

আপনি যদি কোনও কাজ শেষ করতে চান তবে কোনও ক্রিয়াকলাপ সম্পাদন করতে পারেন। একটি ভাল সমাধান হ'ল ঘটনা শোনানো। উদাহরণস্বরূপ, আমি একটি Dispatcher, DispatcherEventES6 সহ একটি শ্রেণি প্রয়োগ করব , তারপরে:

let Notification = new Dispatcher()
Notification.on('Load data success', loadSuccessCallback)

const loadSuccessCallback = (data) =>{
   ...
}
//trigger a event whenever you got data by
Notification.dispatch('Load data success')

ডেস্প্যাচার:

class Dispatcher{
  constructor(){
    this.events = {}
  }

  dispatch(eventName, data){
    const event = this.events[eventName]
    if(event){
      event.fire(data)
    }
  }

  //start listen event
  on(eventName, callback){
    let event = this.events[eventName]
    if(!event){
      event = new DispatcherEvent(eventName)
      this.events[eventName] = event
    }
    event.registerCallback(callback)
  }

  //stop listen event
  off(eventName, callback){
    const event = this.events[eventName]
    if(event){
      delete this.events[eventName]
    }
  }
}

DispatcherEvent:

class DispatcherEvent{
  constructor(eventName){
    this.eventName = eventName
    this.callbacks = []
  }

  registerCallback(callback){
    this.callbacks.push(callback)
  }

  fire(data){
    this.callbacks.forEach((callback=>{
      callback(data)
    }))
  }
}

শুভ কোডিং!

পি / এস: আমার কোডটিতে কিছু ত্রুটি ব্যতিক্রম হ্যান্ডেল অনুপস্থিত



1

কলব্যাক ফাংশন কল করার সময়, আমরা নীচের মত এটি ব্যবহার করতে পারে:

consumingFunction(callbackFunctionName)

উদাহরণ:

// Callback function only know the action,
// but don't know what's the data.
function callbackFunction(unknown) {
  console.log(unknown);
}

// This is a consuming function.
function getInfo(thenCallback) {
  // When we define the function we only know the data but not
  // the action. The action will be deferred until excecuting.
  var info = 'I know now';
  if (typeof thenCallback === 'function') {
    thenCallback(info);    
  }
}

// Start.
getInfo(callbackFunction); // I know now

এটি সম্পূর্ণ উদাহরণ সহ কোডটিড


1

কিছু উত্তর, সঠিক হলেও বুঝতে অসুবিধা হতে পারে। সাধারণ ব্যক্তির শর্তাবলী এখানে একটি উদাহরণ:

var users = ["Sam", "Ellie", "Bernie"];

function addUser(username, callback)
{
    setTimeout(function()
    {
        users.push(username);
        callback();
    }, 200);
}

function getUsers()
{
    setTimeout(function()
    {
        console.log(users);
    }, 100);
}

addUser("Jake", getUsers);

কলব্যাকের অর্থ হল, "জ্যাক" এর সাথে ব্যবহারকারীদের তালিকা প্রদর্শন করার আগে ব্যবহারকারীদের সাথে সর্বদা যুক্ত করা হয় console.log

উত্স (ইউটিউব)


আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.