我需要解释一下。我搜索了一个答案,却找不到答案。
问题如下: 我正在从书中进行练习:“为工程师编程”A.R.布拉德利第7章 这是代码的一部分:
struct _fifo {
unsigned capacity;
unsigned head;
unsigned tail;
void * data[0];
};
fifo newFifo(int capacity) {
// The capacity of a circular buffer is one less than one
// would think: if the user wants a given capacity, the
// required array is one cell larger.
capacity++;
fifo q = (fifo) malloc(sizeof(struct _fifo) + capacity * (sizeof(void *)));
q->capacity = (unsigned) capacity;
q->head = 0;
q->tail = 0;
return q;
}
int putFifo(fifo q, void * e) {
if ((q->head+1) % q->capacity == q->tail) // full?
return -1;
q->data[q->head] = e;
q->head = (q->head+1) % q->capacity;
return 0;
}
typedef void (*printFn) (void*);
int printFifo(fifo q, printFn f) {
unsigned i;
for (i = q->tail; i != q->head; i = (i+1) % q->capacity) {
f(q->data[i]);
}
return 0;
}
static void printLong(void * e) {
// %ld tells printf to print a long integer
printf("%ld", (long) e);
}
int main() {
fifo longq;
longq = newFifo(3);
printFifo(longq, printLong);
return 0;
}
我的问题是: 在函数printLong我传递无效指针e所以演员(长)e使e的地址?为什么我得到数据的价值而不是打印的地址?
例如,如果我这样做,我打印的地址不是值:
typedef void (*printFn) (void*);
static void printLong (void * e) {
printf("%ld", (long) e);
}
int printL (void* l, printFn f) {
f(l);
}
int main()
{
long a = 5;
long* l = &a;
printf("%ld\n", *l);
printL(l, printLong);
return 0;
}
但如果我投了
*(long*) e
我会得到价值。为什么第一个代码部分打印的值不是地址? 我想我没有看到什么,所以这就是为什么我很困惑。请帮助:)
答案 0 :(得分:0)
从我的观点来看,它打印指定值的唯一方法是在指针中手动将它们指定为地址。
示例强>
void * ptr=100;
printf("%ld", (long)ptr);
将在屏幕上打印100
,但尝试取消引用它会导致(最有可能)分段错误。
因此,考虑到这个过程的风险,以及在虚假中保持长整数的无意义*我甚至反对将此视为有用的代码。
答案 1 :(得分:0)
函数printLong中的我正在传递void指针e,所以演员也是如此 (长)e做e的地址?我怎么得到数据的价值 而不是打印的地址?
没有。它将指针强制转换为long int。如果您想获得e的地址,请改用& e。但是e已经是函数的地址......我认为获取参数的地址没有意义,因为它在堆栈中。
所以基本上我猜你可能对函数有一些误解。函数名不像var名:
更新:
我叫f(q-> data [i]);得到printLong(void * e) - 所以不应该e 指向q-> data [i]?
在C中,函数参数按值传递。 q-> data [i]的值被传递给printLong(),因此参数e将具有与q-> data [i]相同的值(相同的地址)。所以e是q-> data [i]
的副本