[jquery] jQuery 연기 및 약속-.then () 대 .done ()

jQuery 지연 및 약속에 대해 읽었 으며 성공적인 콜백에 .then()& .done()를 사용하는 것의 차이점을 볼 수 없습니다 . 나도 에릭 Hynds는 것을 언급 .done().success()같은 기능에 매핑 그러나 나는 그렇게 추측하고있어 .then()모든 콜백 모든 성공적인 작업의 완료에 호출한다.

누구든지 올바른 사용법을 가르쳐 줄 수 있습니까?



답변

done()연기 된 문제가 해결되면 연결된 콜백이 시작 됩니다. fail()지연된 항목이 거부되면 연결된 콜백이 시작 됩니다.

jQuery 1.8 이전에는 then()구문 설탕이었습니다.

promise.then( doneCallback, failCallback )
// was equivalent to
promise.done( doneCallback ).fail( failCallback )

1.8부터는 새로운 약속 then()의 별칭 pipe()이며 반환합니다 . 에 대한 자세한 내용 은 여기 를 참조 하십시오pipe() .

success()그리고 error()온에서만 사용할 수 있습니다 jqXHR호출에 의해 반환 된 객체 ajax(). 그들은을위한 간단한 별칭 done()fail()각각 :

jqXHR.done === jqXHR.success
jqXHR.fail === jqXHR.error

또한 done()단일 콜백으로 제한되지 않으며 비 기능을 필터링합니다 (버전 1.8의 문자열에 1.8.1에서 수정해야하는 버그가 있음).

// this will add fn1 to 7 to the deferred's internal callback list
// (true, 56 and "omg" will be ignored)
promise.done( fn1, fn2, true, [ fn3, [ fn4, 56, fn5 ], "omg", fn6 ], fn7 );

동일합니다 fail().


답변

반환 결과가 처리되는 방식에도 차이가 있습니다 (연결이라고 함, 연결 done하지 않고 then호출 체인 을 생성 함)

promise.then(function (x) { // Suppose promise returns "abc"
    console.log(x);
    return 123;
}).then(function (x){
    console.log(x);
}).then(function (x){
    console.log(x)
})

다음과 같은 결과가 기록됩니다.

abc
123
undefined

동안

promise.done(function (x) { // Suppose promise returns "abc"
    console.log(x);
    return 123;
}).done(function (x){
    console.log(x);
}).done(function (x){
    console.log(x)
})

다음을 얻을 것이다 :

abc
abc
abc

———- 업데이트 :

Btw. 원자 유형 값 대신 Promise를 반환하면 외부 약속이 내부 약속이 해결 될 때까지 기다립니다.

promise.then(function (x) { // Suppose promise returns "abc"
    console.log(x);
    return $http.get('/some/data').then(function (result) {
        console.log(result); // suppose result === "xyz"
        return result;
    });
}).then(function (result){
    console.log(result); // result === xyz
}).then(function (und){
    console.log(und) // und === undefined, because of absence of return statement in above then
})

이러한 방식으로 다음과 같은 병렬 또는 순차적 비동기 작업을 작성하는 것이 매우 간단 해집니다.

// Parallel http requests
promise.then(function (x) { // Suppose promise returns "abc"
    console.log(x);

    var promise1 = $http.get('/some/data?value=xyz').then(function (result) {
        console.log(result); // suppose result === "xyz"
        return result;
    });

    var promise2 = $http.get('/some/data?value=uvm').then(function (result) {
        console.log(result); // suppose result === "uvm"
        return result;
    });

    return promise1.then(function (result1) {
        return promise2.then(function (result2) {
           return { result1: result1, result2: result2; }
        });
    });
}).then(function (result){
    console.log(result); // result === { result1: 'xyz', result2: 'uvm' }
}).then(function (und){
    console.log(und) // und === undefined, because of absence of return statement in above then
})

위의 코드는 두 개의 http 요청을 병렬로 발행하여 요청을 더 빨리 완료하는 반면, http 요청 아래에서 순차적으로 실행되므로 서버로드가 줄어 듭니다.

// Sequential http requests
promise.then(function (x) { // Suppose promise returns "abc"
    console.log(x);

    return $http.get('/some/data?value=xyz').then(function (result1) {
        console.log(result1); // suppose result1 === "xyz"
        return $http.get('/some/data?value=uvm').then(function (result2) {
            console.log(result2); // suppose result2 === "uvm"
            return { result1: result1, result2: result2; };
        });
    });
}).then(function (result){
    console.log(result); // result === { result1: 'xyz', result2: 'uvm' }
}).then(function (und){
    console.log(und) // und === undefined, because of absence of return statement in above then
})


답변

.done() 콜백이 하나 뿐이며 성공 콜백입니다.

.then() 성공과 실패 콜백이 모두 있습니다

.fail() 하나의 실패 콜백이 있습니다

그래서 당신이해야 할 일은 당신에게 달려 있습니다 … 성공했는지 아니면 실패하는지 걱정하십니까?


답변

deferred.done ()

Deferred가 해결 될 때만 호출 핸들러를 추가합니다 . 호출 할 콜백을 여러 개 추가 할 수 있습니다.

var url = 'http://jsonplaceholder.typicode.com/posts/1';
$.ajax(url).done(doneCallback);

function doneCallback(result) {
    console.log('Result 1 ' + result);
}

위와 같이 쓸 수도 있습니다.

function ajaxCall() {
    var url = 'http://jsonplaceholder.typicode.com/posts/1';
    return $.ajax(url);
}

$.when(ajaxCall()).then(doneCallback, failCallback);

deferred.then ()

Deferred가 해결, 거부 또는 여전히 진행 중일 때 호출 핸들러를 추가합니다 .

var url = 'http://jsonplaceholder.typicode.com/posts/1';
$.ajax(url).then(doneCallback, failCallback);

function doneCallback(result) {
    console.log('Result ' + result);
}

function failCallback(result) {
    console.log('Result ' + result);
}


답변

jQuery의 Deferreds가 Promises의 구현으로 간주되는 한 (jQuery3.0은 실제로 스펙을 적용하려고 시도하는 한) 실제로 중요한 차이가 있습니다.

done / then의 주요 차이점은

  • .done() 항상 자신이 무엇을하든, 무엇을 반환하든 관계없이 항상 같은 약속 / 포장 값을 반환합니다.
  • .then() 항상 새 약속을 반환하며, 전달한 함수에 따라 약속의 내용을 제어 할 책임이 있습니다.

jQuery에서 기본 ES2015 Promises로 변환되는 .done()것은 체인이 “해결”상태 인 경우 값이 함수에 전달된다는 점에서 Promise 체인의 함수 주위에 “탭”구조를 구현하는 것과 비슷합니다. 그러나 그 기능의 결과는 체인 자체에 영향을 미치지 않습니다.

const doneWrap = fn => x => { fn(x); return x };

Promise.resolve(5)
       .then(doneWrap( x => x + 1))
       .then(doneWrap(console.log.bind(console)));

$.Deferred().resolve(5)
            .done(x => x + 1)
            .done(console.log.bind(console));

6이 아닌 5를 기록합니다.

나는 done과 doneWrap을 사용하여 로깅을 수행했다. console.log 함수는 실제로 아무것도 반환하지 않기 때문입니다. 그리고 아무것도 반환하지 않는 함수를 전달하면 어떻게됩니까?

Promise.resolve(5)
       .then(doneWrap( x => x + 1))
       .then(console.log.bind(console))
       .then(console.log.bind(console));

그것은 기록 할 것이다 :

5

찾으시는 주소가 없습니다

어떻게 된 거예요? .then을 사용하고 아무것도 반환하지 않는 함수를 전달했을 때 암시적인 결과는 “정의되지 않음”이었습니다. 물론 다음 정의 된 Promise [undefined]를 다음 then 메소드에 반환하여 undefined를 기록했습니다. 우리가 시작한 원래 가치는 기본적으로 없어졌습니다.

.then()핵심은 함수 구성의 형태입니다. 각 단계의 결과는 다음 단계에서 함수의 인수로 사용됩니다. .done이 “탭”으로 가장 잘 생각되는 이유입니다.-> 실제로 컴포지션의 일부가 아니며 특정 단계에서 값을 들여다보고 해당 값에서 함수를 실행하지만 실제로는 변경하지 않는 것입니다. 어떤 식 으로든 구성.

이것은 근본적인 차이점이며, 기본 약속에 .done 메서드가 구현되어 있지 않은 좋은 이유가 있습니다. 우리는 왜 더 .fail 메소드가 없는지 알아낼 필요가 없습니다. 왜냐하면 .fail / .catch는 더 복잡하기 때문입니다 (즉, .fail / .catch는 베어 값을 반환하는 .dach / .then-> 함수의 미러가 아닙니다 “체재”는.


답변

then()항상 어떤 경우에도 호출됩니다. 그러나 매개 변수 전달은 jQuery 버전마다 다릅니다.

jQuery를 1.8 이전에, then()동일done().fail() . 그리고 모든 콜백 함수는 동일한 매개 변수를 공유합니다.

그러나 jQuery 1.8부터 then() 부터는 새로운 약속을 반환하고 값을 반환하면 다음 콜백 함수로 전달됩니다.

다음 예제를 보자.

var defer = jQuery.Deferred();

defer.done(function(a, b){
            return a + b;
}).done(function( result ) {
            console.log("result = " + result);
}).then(function( a, b ) {
            return a + b;
}).done(function( result ) {
            console.log("result = " + result);
}).then(function( a, b ) {
            return a + b;
}).done(function( result ) {
            console.log("result = " + result);
});

defer.resolve( 3, 4 );

jQuery 1.8 이전에 답은

result = 3
result = 3
result = 3

모두 result3이 걸립니다. 그리고then() 함수는 항상 다음 함수 같은 연기 객체를 전달합니다.

그러나 jQuery 1.8 기준으로 결과는 다음과 같아야합니다.

result = 3
result = 7
result = NaN

첫 번째 then()함수는 새로운 promise를 반환하고 값 7 (및 전달할 유일한 매개 변수)이 다음으로 전달 done()되므로 두 번째 done()write result = 7입니다. 두 번째 then()값은 7을 값으로 사용 a하고 두 번째 undefined값은 NaN 매개 변수를 사용하여 새 약속을 반환하고 마지막 은 NaN을 결과로 인쇄합니다.bthen()done()


답변

다른 답변에서 찾기가 매우 어려운 응답에 매우 간단한 정신 매핑이 있습니다.