我试图了解每个源文件方法一个标头背后的目的.正如我所看到的,标题用于typedef在使用它们的几个文件之间共享函数声明,宏和宏.当您为.c文件创建头文件时,它的缺点是每次要查看函数声明或宏时都需要引用头文件,通常一切都在一个源文件(不是整个文件)中更简单软件,当然).
那么为什么程序员会使用这种方法呢?
您如何看待一线功能?这不好吗?我能想到的一个优点是它使代码更加全面(如果你为它选择一个好名字).例如:
void addint(Set *S, int n)
{
(*S)[n/CHAR_SIZE] |= (unsigned char) pow(2, (CHAR_SIZE - 1) - (n % CHAR_SIZE));
}
Run Code Online (Sandbox Code Playgroud)
我能想到的一个缺点是它会减慢代码的速度(将参数推送到堆栈,跳转到函数,弹出参数,执行操作,跳回代码 - 只有一行?)
将这些行放在函数中还是只将它们放入代码中更好?即使我们只使用它们一次?
顺便说一句,我还没有发现任何问题,所以请原谅我以前曾经问过这样的问题.
假设我有这个struct(偶然包含位字段,但你不应该在意):
struct Element {
unsigned int a1 : 1;
unsigned int a2 : 1;
...
unsigned int an : 1;
};
Run Code Online (Sandbox Code Playgroud)
我想以方便的方式访问第i个成员.我们来检查一下检索解决方案.
我想出了这个功能:
int getval(struct Element *ep, int n)
{
int val;
switch(n) {
case 1: val = ep->a1; break;
case 2: val = ep->a2; break;
...
case n: val = ep->an; break;
}
return val;
}
Run Code Online (Sandbox Code Playgroud)
但我怀疑有一个更简单的解决方案.也许是数组访问风格之类的东西.
我试着这样做:
#define getval(s,n) s.a##n
Run Code Online (Sandbox Code Playgroud)
但预计它不起作用.
有更好的解决方案吗?
在"The C Programming Language"一书中,它说:
"当文件出现错误或文件结束时,库中的许多功能都会设置状态指示器.这些指示器可以显式设置和测试.此外,整数表达式
errno(声明<errno.h>)可能包含一个错误编号,提供有关最多的信息.最近的错误."
我在哪里可以看到这些功能的列表?
我试图在以下代码中终止线程:
public synchronized void run() {
try {
while (!Thread.currentThread().isInterrupted()) {
this.scan();
this.distribute();
this.wait();
}
} catch (InterruptedException e) {}
}
public void cancel() {
this.interrupt();
}
Run Code Online (Sandbox Code Playgroud)
但线程不会终止.我使用了调试器并发现在命令之后this.interrupt(),线程没有被中断(我对表达式进行了监视this.isInterrupted()并保持不变false).任何人都知道为什么这个线程不会被打断?
问题已经找到.原来这个帖子有两个实例.我附上导致这个问题的有问题的代码:
/* (class Detector extends Thread) */
Detector detector = new Detector(board);
...
Thread tdetector = new Thread(detector); /* WRONG!!! */
...
tdetector.start();
...
Run Code Online (Sandbox Code Playgroud) 我只希望以下似乎你不喜欢多余的jabber :)
无论如何,有这样的:
for (p = fmt; *p; p++) {
if (*p != '%') {
putchar(*p);
continue;
}
switch (*++p) {
/* Some cases here */
...
}
}
Run Code Online (Sandbox Code Playgroud)
我想知道为什么作家(Kernighan/Ritchie)continue在if声明中使用了它.
我认为这仅仅是因为他认为它比switch在else声明中缩进整体更优雅,你怎么看?
来自维基百科的伪代码:
function Dijkstra(Graph, source):
2 for each vertex v in Graph: // Initializations
3 dist[v] := infinity ; // Unknown distance function from source to v
4 previous[v] := undefined ; // Previous node in optimal path from source
5 end for ;
6 dist[source] := 0 ; // Distance from source to source
7 Q := the set of all nodes in Graph ; // All nodes in the graph are unoptimized - thus are in Q
8 while …Run Code Online (Sandbox Code Playgroud) 有以下声明:
void qsort(void *lineptr[], int left, int right, int (*comp)(void *, void *));
int numcmp(char *, char *);
int strcmp(char *s, char *t);
Run Code Online (Sandbox Code Playgroud)
然后,在程序的某个地方有以下调用:
qsort((void**) lineptr, 0, nlines-1,
(int (*)(void*,void*))(numeric ? numcmp : strcmp));
Run Code Online (Sandbox Code Playgroud)
(忽略前三个参数和numeric).
我问这是什么:
(int (*)(void*,void*))(numeric ? numcmp : strcmp)
Run Code Online (Sandbox Code Playgroud)
我明白,qsort期待一个"指向函数的指针获得两个void指针并返回一个int"作为它的第四个参数,但是上面的内容是如何满足的呢?在我看来,它似乎是某种类型的演员,因为它是由两个括号组成的,但那将是一个非常奇怪的演员.因为它需要一个函数并使这个函数成为"指向函数的指针,它获取两个void指针并返回一个int".这没有意义.
(我在这里遵循一个规则,即type变量之前的括号中的类型将变量提升为该类型).
所以我想我错了,也许有人可以告诉我怎么读这个,订单是什么?
int foo(char *c) {...}
main() {
int (*thud)(void *);
thud = (int (*)(void *))(foo);
}
Run Code Online (Sandbox Code Playgroud)
在评估作业时实际发生了什么?
铸造类型和foo; 之间存在差异; cast类型是一个指针,foo是一个函数.那么,编译器是否将' (foo)'中的内容转换为指针,foo然后才进行转换?因为没有别的东西似乎有意义; 另一个选项是函数本身被转换为一个指向函数的指针,该函数获取void*并返回一个int,据我所知,函数是内存中一段代码的标签,因此不能成为指针,这是一个变量.
假设我有一些迭代器:
val nextElemIter: Iterator[Future[Int]] = Iterator.continually(...)
Run Code Online (Sandbox Code Playgroud)
我想从该迭代器构建一个源代码:
val source: Source[Future[Int], NotUsed] =
Source.fromIterator(() => nextElemIter)
Run Code Online (Sandbox Code Playgroud)
所以现在我的源码发出了Futures.我从来没有看到期货在Akka文档或其他任何地方的阶段之间传递,所以相反,我总是可以这样做:
val source: Source[Int, NotUsed] =
Source.fromIterator(() => nextElemIter).mapAsync(1)(identity /* was n => n */)
Run Code Online (Sandbox Code Playgroud)
现在我有一个常规的源代码T而不是Future[T].但这感觉很糟糕和错误.
处理这种情况的正确方法是什么?
c ×6
c++ ×2
casting ×2
coding-style ×2
function ×2
pointers ×2
akka ×1
akka-stream ×1
algorithm ×1
concurrency ×1
conventions ×1
dijkstra ×1
errno ×1
header ×1
interrupt ×1
java ×1
scala ×1
struct ×1