通过office-js替换许多内容控件的文本的最快方法是什么? [英] What is the fastest way of replacing the text of many content controls via office-js?

查看:129
本文介绍了通过office-js替换许多内容控件的文本的最快方法是什么?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我编写了以下函数来替换大量具有指定值的CC:

  / ** replaceManyCCs()
*
*根据replacementObject替换许多内容控件的内容。
*
* @arg replacementObject字典。密钥是应该替换的CC的标题。值是替换值。
* /
函数replaceManyCCs(replacementObject){
Word.run(function(context){
var time1 = Date.now();

//加载所有内容控件的标题
var CCc = context.document.contentControls.load('title');

返回context.sync()。then(function(){ //同步
//提取CC标题
var documentCCtitleList = [];
for(var i = 0; i< CCc.items.length; i ++){documentCCtitleList.push(CCc) .items [i] .title);}

//检查缺少的标题并替换
var replaceCounter = 0;
for(var对象在replacementObject中){
var index = documentCCtitleList.indexOf(key);
if(index == -1){// title缺少
throw'无法找到带标题的CC''+ key +'';
}
else {//替换
CCc.i tems [index] .insertText(''+ replacementObject [key],'Replace');
replaceCounter ++;
}
}

$('#status')。html('... replacement ...');

返回context.sync()。then(function(){
var time2 = Date.now();
var tdiff = time2-time1;
$ ('#status')。html('替换'+ replaceCounter +'CCs in'+(tdiff / 1000)+'秒');
});
});
})。catch(函数(错误){
$('#status')。html('< pre>错误:'+ JSON.stringify(错误,null,4)+'< ; / pre>');
console.log('错误:'+ JSON.stringify(error,null,4));
if(错误实例OfficeExtension.Error){
console .log('Debug info:'+ JSON.stringify(error.debugInfo,null,4));
}
});
}

使用此代码替换816 CC需要50-60秒。有没有更好/更快的方法来实现这个目标?

解决方案

良好的跟进问题。我需要知道有关replacementObject数组有多大的更多细节我假设至少与文档中的内容控件的大小相同,这肯定会直接影响方法的整体性能。正如您所见

我认为您应该标记(或标题)每个内容使用直接将其映射到relacementObject数组位置的索引进行控制(title =在替换对象中使用index,直接使用replacementObject数组的索引来更改单个遍中的值。如果有办法,那么你将使用得到最快的结果!


I wrote the following function to replace a huge amount of CCs with specified values:

/** replaceManyCCs()
 *
 * Replaces the content of many content controls, based on the replacementObject.
 *
 * @arg replacementObject   A dictionary. The keys are the titles of the CCs which should be replaced. The values are the replacement values.
 */
function replaceManyCCs (replacementObject) {
    Word.run(function (context) {
        var time1 = Date.now();

        // load the title of all content controls
        var CCc = context.document.contentControls.load('title');

        return context.sync().then(function () { // synchronous
            // extract CC titles
            var documentCCtitleList = [];
            for(var i = 0; i < CCc.items.length; i++) { documentCCtitleList.push(CCc.items[i].title); }

            // check for missing titles and replace
            var replaceCounter = 0;
            for(var key in replacementObject) {
                var index = documentCCtitleList.indexOf(key);
                if(index == -1) { // title is missing
                    throw 'Could not find CC with title "'+key+'"';
                }
                else { // replace
                    CCc.items[index].insertText(' '+replacementObject[key], 'Replace');
                    replaceCounter++;
                }
            }

            $('#status').html('...replacing...');

            return context.sync().then(function () {
                var time2 = Date.now();
                var tdiff = time2-time1;
                $('#status').html('Replaced '+replaceCounter+' CCs in '+(tdiff/1000)+' seconds');
            });
        });
    }).catch(function (error) {
        $('#status').html('<pre>Error: ' + JSON.stringify(error, null, 4) + '</pre>');
        console.log('Error: ' + JSON.stringify(error, null, 4));
        if (error instanceof OfficeExtension.Error) {
            console.log('Debug info: ' + JSON.stringify(error.debugInfo, null, 4));
        }
    });
}

Replacing 816 CCs requires 50-60 seconds with this code. Are there any better/faster ways of accomplishing this?

解决方案

good follow up question. I would need to know more details about how big the replacementObject array is I am assuming at least the same size as the # of content controls in the document, that definitely has direct impact on the overall perf of your method. As you can see from my previous answer, updating 700 CCs with a fixed value takes no more than 5 seconds, so I think the satellite operations you are doing to find the new values are affecting negatively the performance.

Specifically, I see a couple of things you are doing that impact negatively the perf, and you could potentially fix.

  1. You are traversing at least 2 times the content control collection. One for getting the titles (and push them into a temp array), and another one to replace the content (if the replacement object matched the CCs in the doc). I would really try to do this in a single pass.
  2. On top of the above, In the inner loop where you are finding the titles, you are practically traversing the replacementObject for each CC (this means at least you are traversing this array 700 times) and to make things worse you are using the array.indexOf method to find the index by key (just FYI in the browser we use for Add-ins, latest IE, this is the most expensive way of traversing an array, in fact is 90% slower than if you do a for loop trying to find the indesx given the key, this simple change theoretically will be 90% faster in latest IE, if you want to keep this logic). Check out this page demonstrating this (use latest IE browser for test).

I think you should tag (or title) each content control with the index that directly maps it to the relacementObject array position (title=index in the replacement object and just directly use the index of the replacementObject array to change the values in a single pass. If there is a way of doing that you will get the fastest outcome!

这篇关于通过office-js替换许多内容控件的文本的最快方法是什么?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆