Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/445.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript RxJS等待上一次执行完成_Javascript_Rxjs - Fatal编程技术网

Javascript RxJS等待上一次执行完成

Javascript RxJS等待上一次执行完成,javascript,rxjs,Javascript,Rxjs,好吧,我是RxJs的新手,我想不出什么。 我需要实现图像处理,其中用户一次添加多个图像,对于每个图像,必须执行以下操作: 在web worker中生成图像缩略图 将图像和缩略图上载到服务器 但我不希望一次生成所有缩略图,我希望它们按顺序生成。以下是我尝试过的: 我还将在此处粘贴代码: 从“rxjs”导入{of}; 从“rxjs/operators”导入{map}; 常量imageObservable=of(1,2,3,4,5); 函数generateThumbnail(图像){ log(`Gen

好吧,我是RxJs的新手,我想不出什么。 我需要实现图像处理,其中用户一次添加多个图像,对于每个图像,必须执行以下操作:

  • 在web worker中生成图像缩略图
  • 将图像和缩略图上载到服务器
  • 但我不希望一次生成所有缩略图,我希望它们按顺序生成。以下是我尝试过的:

    我还将在此处粘贴代码:

    从“rxjs”导入{of};
    从“rxjs/operators”导入{map};
    常量imageObservable=of(1,2,3,4,5);
    函数generateThumbnail(图像){
    log(`Generating thumbnail${image}`);
    返回新承诺(解决=>{
    设置超时(()=>{
    log(`Finished generating thumbnail${image}`);
    决心({
    形象,,
    缩略图:`这是图像${image}的缩略图`
    });
    }, 1500);
    });
    }
    异步函数上传(imagePromise){
    常量图像=等待图像承诺;
    控制台日志(“上传”,图像);
    返回新承诺(解决=>{
    设置超时(()=>{
    console.log(“已完成上传”,图像);
    解决();
    }, 1500);
    });
    }
    imageObservable.pipe(map(generateThumbnail)).subscribe(upload);
    

    我希望RxJS等待previous
    generateThumbnail
    以执行当前调用(这就是它返回承诺对象的原因),并等待previous
    upload
    以执行当前调用(因此
    upload
    也返回承诺)。我不知道如何做到这一点。有RxJS忍者愿意帮我吗?

    你只想按顺序生成缩略图,还是第二个缩略图的生成也需要等待第一个缩略图的上传完成

    如果您不想等待上传,只需将其锁定:

    import { of, from, } from 'rxjs';
    import { concatMap } from 'rxjs/operators';
    
    const imageObservable = of(1, 2, 3, 4, 5);
    
    function generateThumbnail(image) {
        console.log(`Generating thumbnail ${image}`);
        return new Promise(resolve => {
            setTimeout(() => {
                console.log(`Finished generating thumbnail ${image}`);
                resolve({
                    image,
                    thumbnail: `This is a thumbnail of image ${image}`
                });
            }, 1500);
        });
    }
    
    async function upload(imagePromise) {
        const image = await imagePromise;
        console.log('Uploading', image);
        return new Promise(resolve => {
            setTimeout(() => {
                console.log('Finished uploading', image);
                resolve();
            }, 1500);
        });
    }
    
    // imageObservable.pipe(map(generateThumbnail)).subscribe(upload);
    
    imageObservable.pipe(concatMap(image => from(generateThumbnail(image)))).subscribe();
    
    做你想做的事,我只是用你的
    承诺
    创意运营商的
    做了一个
    可观察的
    ,我认为这是不必要的。但是使用RxJs时,通常更容易使用
    可观察对象
    而不是
    承诺

    function generateThumbnail(image): Observable<any> {
        console.log(`Generating thumbnail ${image}`);
        return from(
            new Promise(resolve => {
                setTimeout(() => {
                    console.log(`Finished generating thumbnail ${image}`);
                    resolve({
                        image,
                        thumbnail: `This is a thumbnail of image ${image}`
                    });
                }, 1500);
            })
        );
    }
    

    要实现以下目标:

  • 缩略图生成应按顺序进行,顺序很重要=>使用concatMap
  • 应在生成缩略图后立即进行上载
  • 上传可以按并行顺序进行并不重要=>使用地图
  • 所以最终的代码可能是

    imageObservable
      .pipe(
        // preserve orders and wait for previous observable
        concatMap(generateThumbnail), 
    
        // map the generate
        map(upload)
      )
      .subscribe();
    
    注意:上传不会等待generateThumbnail承诺,因为这应该由concatMap自己处理


    generateThumbnail是否也应该等待上一次上传?不,不应该。很酷,看起来它可以解决我的问题,我会试试,谢谢!另外-是否可以让上传也等待上一次(我的意思是-上一次上传)?无法再编辑评论-我认为可以对concatMap使用相同的方法,但在这种情况下,上传是订阅者,而不是过滤器。这是空的
    subscribe()
    call cosidered当然是一个“干净”的解决方案。我喜欢所有的东西都使用管道操作符,这样更容易扩展。我通常看到的
    subscribe
    与“ok now execute the pipeline”一模一样。谢谢!但基本上这似乎是ritaj建议的解决方案
    imageObservable
      .pipe(
        // preserve orders and wait for previous observable
        concatMap(generateThumbnail), 
    
        // map the generate
        map(upload)
      )
      .subscribe();
    
    async function upload(image) {
      console.log(`[upload] start ${image.image}`);
      return new Promise(resolve => {
        setTimeout(() => {
          console.log(`[upload] done ${image.image}`);
          resolve();
        }, 1000);
      });
    }