Tough Programming Interview Questions and Notes
(Includes Frequently asked Interview questions in Bangalore IT industry)
Typedef vs Macro
1.Even though typedef and macro seem to be same but there implementation is different.Typedef is a alternate name to the existing data types.Whereas macro is just the preprocessor replacement of the name to corresponding name.
typedef with pointers cannot be implemented using macros for ex:
typedef int* myint;//typedef int *myint;
#define urint int*;
myint a,b;
urint c,d;
Here a,b,c are pointers and d is just an int.
unsigned urint//legal
unsigned myint //illegal
2.
struct Node {
int data;
struct Node *nextptr;
}node;//object
typedef struct Node {
int data;
struct Node *nextptr;
}node_t;//datatype
3.Using typedef for typecast
typedef int (*funcptr)(double);
funcptr x = (funcptr) NULL;
4. typedef int Array[10];
Array becomes a data type for an array of 10 integers. i.e. Array my_arr; declares my_arr as an array of 10 integers .
int (*p1d)[10];
p1d here is a pointer to an array of 10 integers
int *p1d[10];
which would make p1d the name of an array of 10 pointers to type int.
2.Object file
Object file is a set of machine language instructions which are used by linker to create executable file.Compiler creates object files for all the source files and prepares a symbol table.It contains local,global and external references.Its the job of the linker to match up the external references with the global definitions in different object files.
3.Makefile
Its like a batch file where we can run the unix commands.Basically used to compile large projects.
Sample:
CC=gcc
CFLAGS=-g -D__DEBUG__
CLIBS = -lsqlite3 -lacctl -lrt
APPLICATION_NAME = xyz
ONE_DIR = folder1
TWO_DIR = folder2
OBJS = $(wildcard *.c)
run:
cp -r ../$(ONE_DIR )/* ./; \
cp -r ../$(TWO_DIR )/* ./; \
$(CC) $(CFLAGS) -o $(APPLICATION_NAME) $(OBJS) $(CLIBS); \
./$(APPLICATION_NAME); \
clean:
rm $(APPLICATION_NAME)
3.Sockets Communication
1.Sockets are the interface between application process and transport layer.
Application process comes under User space whereas transport layer comes under kernel space.
2.Three things need to be set in order to create a socket
1.Domain:AF_UNIX or AF_INET
2.Type:Connectionless/Connection oriented,reliable/unreliable,virtual circuits/datagrams
3.protocol:TCP/IP or UDP
3.Analogy for Socket communication(TCP/IP)
server
1.socket():Purchase a mobile phone
2.Bind():Put SIM,Give it a number
3.Listen():Set how many calls you can receive (queue length)
4.accept():Wait for someone to call
//accept returns a new socket fd.That is used in send/recv
5.send(),recv():Do chit chat
6.close():hang up
client
1.socket():
2:connect():Call to a number
3:send/recv:
4:close():
4.For UDP
server: socket(),bind(),sendto(),recvfrom()
client: socket(),sendto(),recvfrom()
5.Socket fd
Socket file description mainly consists of server/client address,port and domain information.
6.Non blocking
using select(),poll() functions, event can be raised in server when fd is ready to take up the requests from the server.
4.extern “c”
The extern "C" line tells the compiler that the external information sent to the linker should use C calling conventions and name mangling (e.g., preceded by a single underscore). Since name overloading isn't supported by C, you can't make several overloaded functions simultaneously callable by a C program.
syntax:
extern “C”
{
}
or
extern “C” void foo();
5.signed/unsigned
The signed value gets promoted to an unsigned value for the comparison and ends up being very large.
signed int s = -1;
unsigned int u=2;
if(u>s)
printf(“u>s”);
else
printf(“s>u”);
Output:s>u
here s behaves like 2^32 - 1
6.Base 64
Base64 is a generic term for any number of similar encoding schemes that encode binary data by treating it numerically and translating it into a base 64 representation.Base64 encoding schemes are commonly used when there is a need to encode binary data that needs be stored and transferred over media that are designed to deal with textual data. This is to ensure that the data remains intact without modification during transport.In other sense Base 64 encoding converts non printable characters into printable characters.ASCII is Base 128(2^7).So Base 64 forms the packs of 6bits from the binary data.
7.XML
1.XML (Extensible Markup Language) is a set of rules for encoding documents in machine-readable form.
2.Key Terminologies:Unicode,XML parser,Markup and Content,Tag,Element,Attribute,XML declaration.
3.Escaping:XML provides escape facilities for referencing problematic or unavailable characters. There are five predefined entities: < represents "<", > represents ">", & represents "&", ' represents ', and " represents ".
8.TIPS
1.Copy from one structure to another.
Ex:
struct _t a,b;
a = b;
or
memcpy(&a,&b,sizeof(a));
2.Copy constructor used to create a new object as a copy of an existing object.
C++ supports default shallow copies.
There are 3 important places where a copy constructor is called.
- When an object is created from another object of the same type
- When an object is passed by value as a parameter to a function
- When an object is returned from a function
Ex:Person a;Person b(a);or Person b = a;3.Public,Private,Protected - Public variables, are variables that are visible to all classes.
- Private variables, are variables that are visible only to the class to which they belong.
- Protected variables, are variables that are visible only to the class to which they belong, and any subclasses.
Publicly Derived:Public - Public ; Protected - Protected
Privately Derived:Public,Protected - Private
Protected Derived:Public,Protected - protected
4.By default the members of structures are public while that for class is private.
5.Memory Structure:Code Segment,Data Segment:Initialized & Uninitialized(.bss)Ex:Global and Static variables
Heap:Dynamic memory allocation
stack:Local variables,Return address;
6.Precedence
Operators Associativity
( [ - . Left to right
! - ++ -{- + * & (type-cast) sizeof Right to left
(in the above line, +, - and * are the unary forms)
* / % Left to right
+ - Left to right
<< >> Left to right
< <= > >= Left to right
== != Left to right
& Left to right
^ Left to right
| Left to right
&& Left to right
|| Left to right
?: Left to right
= += -= *= /= %= &= ^= |= <<= >>= Right to left
, Left to right
7.string constant table is formed by compiler therefore char *p = “Hello” works
8.Overloading and Overriding
Two very important concepts in object-oriented programming are overriding and overloading. Overloading is about creating multiple methods with the same name, but different signatures, in the same scope. Overriding is about changing the behavior of a certain method in the child class from the way it is behaving in the parent class.
9.Namespace
In general, a namespace is an abstract container providing context for the items (names, or technical terms, or words) it holds and allowing disambiguation of homonym items having the same name (residing in different namespaces).
namespace Box1{
int boxSide = 4;
}
namespace Box2{
int boxSide = 12;
}
int main () {
cout << Box1::boxSide << endl; //output 4
cout << Box2::boxSide << endl; //output 12
return 0;
}
10.sizeof
struct a
{
int count;
char name;
int last;
};
char charray[10];
char *chptr = charray;
sizeof(int)=4,sizeof(float)=4,sizeof(char)=1,sizeof(charray)=10,sizeof(chptr)=4,sizeof(struct a)=12//Padding is done to make it multiple of 4(Data structure alignment)
10.a Passing ptr to a ptr of array of structure
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
typedef struct a
{
int count;
char name;
int last;
}one;
int get(one** tt)
{
one *a = (one*)calloc(3,sizeof(one));
*tt = a;
printf("tt in get=%p a = %p\n",tt,a);
a->count = 10;
a->name = 'r';
a++;
a->count = 100;
return 1;
}
main()
{
one *tt = NULL;
get(&tt);
printf("tt after get=%p\n",tt);
printf("%c,%d",tt->name,tt->count);
tt++;
printf(",%d",tt->count);
}
11.
char *pt = (char*)calloc(20,1);
strcpy(pt,"treasure");
char *pt1 = (char*)calloc(20,1);
while(*pt1++ = *pt++);
printf("%ss",pt1,);
Output:
s
Because pt1 points to the end of the string
printf("%ss",pt1-9); would print treasures
12.
int i=10;
printf("%d-%d",--i,i++);
O/P:10-10
Because parameters are passed from right to left
13.A varchar or Variable Character Field is a set of character data of indeterminate length.Its popularly used in DBMS because it provides faster access and unlike the fixed-size char data-type, varchar does not store any blank characters, reducing the size of a database when the full length of the field is not used, although the length of the used size is stored, adding a small overhead.
14.SMP(Symmetric multiprocessor):Many processors share a common Main Memory leading to parallel computing.Load is shared evenly by all the processors with the support from single OS
15.Multi-Core:Many processors inside a single processor
16.A superscalar CPU architecture implements a form of parallelism called instruction level parallelism (ILP)within a single processor.The performance can be improved by executing different sub-steps of sequential instructions simultaneously (this is pipelining), or even executing multiple instructions entirely simultaneously as in superscalar architectures.
17.VLIW(Very Large Instruction Word):The VLIW approach, on the other hand, executes operations in parallel based on a fixed schedule determined when programs are compiled. Since determining the order of execution of operations (including which operations can execute simultaneously) is handled by the compiler, the processor does not need the scheduling hardware.
18.Vector processor instructions that operate on one dimensional array whereas scalar processor instructions operate on single data.SIMD(Single Inst Multiple Data)(Data Level Parallelism),MIMD.
19.A translation lookaside buffer (TLB) is a CPU cache that memory management hardware uses to improve virtual address translation speed. It was the first cache introduced in processors. All current desktop and server processors (such as x86) use a TLB.
20.Nice tutorial on IP:http://compnetworking.about.com/od/workingwithipaddresses/l/aa042900a.htm
OS Concepts:
1.In computer science, a semaphore is a protected variable or abstract data type that constitutes a classic method of controlling access by several processes to a common resource in a parallel programming environment.
2.A deadlock is a situation wherein two or more competing actions are each waiting for the other to finish, and thus neither ever does.
3.Race Condition:Here the result of the process is unexpectedly and critically dependent on the sequence or timing of other events.
4.Thrashing is a situation where large amounts of computer resources are used to do a minimal amount of work, with the system in a continual state of resource contention.
5.A reentrant mutex is a mutual exclusion mechanism. In a reentrant mutex, the same thread can acquire the lock multiple times. However, the lock must be released the same number of times or else other threads will be unable to acquire the lock.
6.Big Endian:The most significant byte (MSB) value is stored at the memory location with the lowest address.Little Endian :LSB(Least significant byte) value of a word is stored at the memory allocation with lowest address.
SQLITE3
1.Creating database and table
char *szErrMsg = NULL;
int rval = 0;
sqlite3 *dbhandle=NULL;
/* open database */
sqlite3_open(DB_PATH, &dbhandle);
/* create offline transaction table */
rval = sqlite3_exec(dbhandle, "create table customer(id VARCHAR(255),\
name VARCHAR(255), date VARCHAR(255),\
time VARCHAR(255), amount VARCHAR(255) );", NULL, NULL, &szErrMsg);
if(rval != SQLITE_OK)
{
printf("1:Sqlite Error = %s\n", szErrMsg);
sqlite3_free(szErrMsg);
szErrMsg = NULL;
}
//insert the value
sqlite3_exec(dbhandle,”insert into transfer (id,name,date,time, \
amount) values \
(‘123','rrr',’21/08/10’,'23:23:45','500') “, NULL, NULL, szErrMsg);
2.Reading Database:
sqlite3 *dbhandle=NULL;
int rval = 0,i;
int nRows=0, nCols=0;
char *szErrMsg = NULL;
char **qResults = NULL;
bank_ctx *array_bctx;
/* open database */
sqlite3_open(DB_PATH, &dbhandle);
//Fetch data from the database
rval = sqlite3_get_table(dbhandle, "select * from customer", &qResults, &nRows, &nCols,
&szErrMsg);
if(rval != SQLITE_OK)
{
printf("SQL select error: %s\n", szErrMsg);
sqlite3_free(szErrMsg);
sqlite3_close(dbhandle);
szErrMsg = NULL;
return(-1);
}
/* all the data selected from the query will be stored in the qResults and
* the no of rows selected will be in the nRows. */
if(nRows>0)
{
printf("rows:%d,cols:%d/n",nRows,nCols);
array_bctx = (bank_ctx*)calloc(nRows + 1,sizeof(bank_ctx));
//assign the pointer value to abctx reference
*abctx = array_bctx;
for(i=0;i<nRows;i++)
{
strcpy(array_bctx[i].id,qResults[(i+1)*nCols+0]);
strcpy(array_bctx[i].name,qResults[(i+1)*nCols+1]);
strcpy(array_bctx[i].date,qResults[(i+1)*nCols+2]);
strcpy(array_bctx[i].time,qResults[(i+1)*nCols+3]);
strcpy(array_bctx[i].amount,qResults[(i+1)*nCols+4]);
}
}
sqlite3_free_table(qResults);
sqlite3_close(dbhandle);
return nRows;
Base 64 Encoder and Decoder
*Base64 Encoder*/
/*user needs to free the return value*/
char* base64_encode(const unsigned char *input, int length)
{
BIO *bmem, *b64;
BUF_MEM *bptr;
b64 = BIO_new(BIO_f_base64());
bmem = BIO_new(BIO_s_mem());
b64 = BIO_push(b64, bmem);
BIO_write(b64, input, length);
BIO_flush(b64);
BIO_get_mem_ptr(b64, &bptr);
char *buff = (char *)malloc(bptr->length);
memcpy(buff, bptr->data, bptr->length-1);
buff[bptr->length-1] = 0;
BIO_free_all(b64);
return buff;
}
int isbase64(char c)
{
return c && strchr(table, c) != NULL;
}
inline char value(char c)
{
const char *p = strchr(table, c);
if(p) {
return p-table;
} else {
return 0;
}
}
int UnBase64(unsigned char *dest, const unsigned char *src, int srclen)
{
*dest = 0;
if(*src == 0)
{
return 0;
}
unsigned char *p = dest;
do
{
char a = value(src[0]);
char b = value(src[1]);
char c = value(src[2]);
char d = value(src[3]);
*p++ = (a << 2) | (b >> 4);
*p++ = (b << 4) | (c >> 2);
*p++ = (c << 6) | d;
if(!isbase64(src[1]))
{
p -= 2;
break;
}
else if(!isbase64(src[2]))
{
p -= 2;
break;
}
else if(!isbase64(src[3]))
{
p--;
break;
}
src += 4;
while(*src && (*src == 13 || *src == 10)) src++;
}
while(srclen-= 4);
*p = 0;
return p-dest;
}
Reading a file
char* get_file(char* path)
{
FILE * pFile;
int lSize;
char * buffer;
char *szbase64 = 0;
size_t result;
#ifdef __DEBUG__
printf("FP Image Path:%s\n",path);
#endif
pFile = fopen ( path , "rb" );
if (pFile==NULL) {fputs ("File error",stderr); exit (1);}
// obtain file size:
fseek (pFile , 0 , SEEK_END);
lSize = ftell (pFile);
rewind (pFile);
printf("\ntemplate length : %d\n",lSize);
// allocate memory to contain the whole file:
buffer = (char*) malloc (sizeof(char)*lSize);
if (buffer == NULL) {fputs ("Memory error",stderr); exit (2);}
// copy the file into the buffer:
result = fread (buffer,1,lSize,pFile);
if (result != lSize) {fputs ("Reading error",stderr); exit (3);}
/* the whole file is now loaded in the memory buffer. */
// terminate
fclose (pFile);
return buffer;
}
Windows Timers
There are 4 types of timers in windows
1.settimer-attaches a timer to a window.Timer expiry is notified through message queue(Ex:WM_QUEUE)
2.Multimedia timers:They are high precision timers which use their own threads to raise the timing events.High CPU overhead and consumes more resources.Ex:timeSetEvent.Need to use minimum resolution to increase the accuracy.
3.Waitabletimer:Here timer blocks the thread which has created the waitable timer.
4.Queue timer:Light weight kernal objects.Timer is implemented by using thread from windows thread pool.