通过引用和复制/恢复之间的区别是什么

时间:2012-01-13 09:33:37

标签: terminology parameter-passing rpc

引用和复制/恢复之间的结果有何不同?

背景:我目前正在研究分布式系统。关于远程过程调用的参考参数的传递,该书指出:“通过引用的调用已被复制/恢复替换。虽然这并不总是相同,但它已经足够了”。我理解原则上如何通过引用和复制/恢复工作,但我没有看到结果的差异在哪里?

3 个答案:

答案 0 :(得分:17)

取自here的例子。

主要代码:

#include <stdio.h>

  int a;

  int main() {
      a = 3;
      f( 4, &a );
      printf("&#37;d\n", a);
      return 0;
  }

按值调用:

f(int x, int &y){
    // x will be 3 as passed argument
    x += a;
    // now a is added to x so x will be 6
    // but now nothing is done with x anymore
    a += 2*y;
    // a is still 3 so the result is 11
}

传入值并且对传入的变量的值没有影响。

按参考号召集:

f(int x, int &y){
    // x will be 3 as passed argument
    x += a;
    // now a is added to x so x will be 6
    // but because & is used x is the same as a
    // meaning if you change x it will change a
    a += 2*y;
    // a is now 6 so the result is 14
}

传入参考。有效地,函数中的变量与外部变量相同。

使用复制/还原进行呼叫:

int a;
void unsafe(int x) {
    x= 2; //a is still 1
    a= 0; //a is now 0
}//function ends so the value of x is now stored in a -> value of a is now 2

int main() {
    a= 1;
    unsafe(a); //when this ends the value of a will be 2
    printf("%d\n", a); //prints 2
}

传入值并且对函数结尾处传递的变量值没有影响,此时函数变量的FINAL值存储在传入的变量中。

通过引用调用和复制/恢复之间的基本区别是,对函数变量的更改将不会显示在传入的变量中,直到函数结束后才会立即看到引用调用的变化。 / p>

答案 1 :(得分:8)

通过复制/恢复进行呼叫是一种特殊情况的呼叫引用,其中提供的引用对于呼叫者是唯一的。在函数结束之前,不会保存引用值的最终结果。

当通过引用调用RPC中的方法时,这种类型的调用很有用。实际数据将发送到服务器端,最终结果将发送到客户端。这将减少流量,因为服务器不会每次都更新引用。

答案 2 :(得分:0)

引用调用:
在按引用调用中,我们传递一个指向被调用函数的指针。该指针指向的数据发生的任何更改都将立即反映出来。
假设如果要对该数据进行大量更改,虽然不会在本地产生太多成本,但在网络成本方面会很昂贵,因为每次更改数据都必须复制回客户端。
C 代码

 void addTwo(int *arr, int n){
  for(int i=0;i<n;i++){
    arr[i]+=2;  //change is happening in the original data as well
  }
}
 int main(){
  int arr[100]={1,2,3,...}; // assuming it to be initialised
  addTwo(arr,100);  
}

通过复制/恢复调用:
在 call-by-copy/restore 中,思想是当函数被调用时引用数据,只有对数据所做更改的最终结果被复制回原始数据(当函数即将return) 在函数调用过程中不对原始数据做任何改动,只需要一次传输回客户端。
在下面的 C 代码中,arr 指向的数据被复制到函数中,并在对本地数据的所有更改完成后存储回 arr
C 代码

 void addTwo(int *arr, int n){
  // copy data locally
  larr = (int*)malloc(n*sizeof(int));
  for(int i=0;i<n;i++){
    larr[i]=arr[i]; 
  }
  for(int i=0;i<n;i++){
    // change is happening to the local variable larr
    larr[i]+=2;  
  }
  //copy all the changes made to the local variable back to the original data
  for(int i=0;i<n;i++){
    arr[i]=larr[i]; 
  }
}

 int main(){
  int arr[100]={1,2,3,...}; // assuming it to be initialised
  addTwo(arr,100);  
}

注意:上面显示的代码不代表实际的 RPC 实现,只是概念的说明。在真正的 RPC 中,消息中传递的是完整的数据,而不是指针(地址)。