Tuesday, September 3, 2013

Technical Debt


This article has got published at -
http://www.mbaskool.com/business-articles/operations/7910-technical-debt-causes-and-solutions.html

History –

Ward Cunningham, a software engineer from America coined this terminology in 1992. He is one of the pioneers of programming methodology like extreme programming. With his several years of experience and innovative ideas, he has been adding new terms to software dictionary.

What is Technical Debt?

Lets us first recall the meaning of the term Debt. As we know very well, debt word is used in financial domain frequently which means a kind of monetary libality of a party or individual.
Debt is a sort of bond on somebody for accomplishing the agreed contract work.

The same concept gets applied to technology field. Widely used in software development field, technical debt talks about the tasks not accomplished which were supposed to be part fo the entire project work.
A system can be in the state of completion with technical debt but definetely contains hidden deficiencies which mars the quality.

In the beginning, the pending activities do not stop the servival or continuation of the project and do not appear fatal to project life cycle. But these works do add values to the project deliverables and the development work.

Moving ahead, the heap of the pending tasks gets large and starts impacting the quality of the work badly.
Lets us have an example to get it understood –

Consider the case of developing a software product handling life cycle of capital market financial product like equity & derivatives.
The well progressing development has some flaws where some sleeping partners are not adding the test cases as part of automated testing. The missing test cases are compensated by the manual testing work.
The tight scheduled project with lack of code review has allowed this to creep in and this pending tasks has started technical debt pool.

Though in the beginning it is not appearing as load, for the subsequent work in the same area will require repeated manual testing. So the debt will be punishing the developer to carry out manual testing every time and make the testing work inefficient.
Also, this will be forever and will make the person its pray who is working on the piece of code.

One can imagine the scene where new functionality are being added to the existing system and will require manual regression testing because of missing test cases or the technical debt.

Prominent Causes –

1. Individual Poor performance-
Poor performance from a technical person will allow initiating such deficiency in the system. Individual level low quality performance is one of the prominent causes of this debt which gets added upon as the system grows.

2. Inefficient Quality & Control Mechanism -

Lack of good review techniques and implementation of the technical works accomplished are another strong reason of such debt creation. Review should be accompanied with appropriate changes and feedback.

3. Carry forward of the debt -

Usually the new person carries forward the technical debt created by the earlier person on the same work.
Many times, in big systems it becomes difficult to get rid of such earlier backlogs and the debt appears as permanent hindrance.

4. Nature of the Biz need -

Tight scheduled biz requirements many times do not provide scope for tracking the technical debts and thus
compromise with the quality of the work. This factor is something out of the control of the technical team.

5. Other factors -

There could be other factors as well like - poor management support, lack of quality standards, inefficient organization technical culture, lack of leadership etc.

Some of the remedies –

Few steps to overcome this scenario are -

1. Adhere to good technical standards and quality practices.
2. Adopt practices for reducing the technical debt with the ongoing works.
3. Developing the environment for individuals to take proactive steps for avoidance of initiating technical debt.
4. Training and awareness for such aspects
Lets us enjoy our technical work without having future debts!

Wednesday, August 21, 2013

Python Threading Features



Threading

What is threading?
Light weight process

Benefits
Shared resources
Switching of threads
Efficient utilization of CPU etc.

Python Module
thread

Contents of the module ‘thread’ -
['LockType', '__doc__', '__name__', '__package__', '_count', '_local', 'allocate', 'allocate_lock', 'error',
'exit', 'exit_thread', 'get_ident', 'interrupt_main', 'stack_size', 'start_new', 'start_new_thread']
e.g. -

import thread
import time

# thread function

def print_time( threadName, delay):
count = 0
while count < 5:
time.sleep(delay)
count += 1
print "%s: %s" % ( threadName, time.ctime(time.time()) )
# Create threadds
try:

thread.start_new_thread( print_time, ("Thread-1", 2, ) )
thread.start_new_thread( print_time, ("Thread-2", 4, ) )
except:
print "Error: unable to start thread"
O/p -
Thread-1: Thu Aug 06 15:42:17 2013
Thread-1: Tue Aug 06 15:42:19 2013
Thread-2: Tue Aug 06 15:42:19 2013
Thread-1: Tue Aug 06 15:42:21 2013
Thread-2: Tue Aug 06 15:42:23 2013
Thread-1: Tue Aug 06 15:42:23 2013
Thread-1: Tue Aug 06 15:42:25 2013
Thread-2: Tue Aug 06 15:42:27 2013
Thread-2: Tue Aug 06 15:42:31 2013
Thread-2: Tue Aug 06 15:42:35 2013

Python Module
threading ( Part of Python 2.4 )

Content of Threading Module
['BoundedSemaphore', 'Condition', 'Event', 'Lock', 'RLock', 'Semaphore', 'Thread', 'ThreadError', 'Timer',
'_BoundedSemaphore', '_Condition', '_DummyThread', '_Event', '_MainThread', '_RLock',
'_Semaphore', '_Timer', '_VERBOSE', '_Verbose', '__all__', '__builtins__', '__doc__', '__file__', '__name__',
'__package__', '_active', '_active_limbo_lock', '_after_fork', '_allocate_lock', '_counter', '_enumerate', '_format_exc', '_get_ident', '_limbo', '_newname', '_pickSomeNonDaemonThread',
'_profile_hook', '_shutdown', '_sleep', '_start_new_thread', '_sys', '_test', '_time', '_trace_hook', 'activeCount', 'active_count', 'currentThread', 'current_thread', 'enumerate', 'local',
'setprofile', 'settrace', 'stack_size', 'warnings']

Content of Threading.Thread class
_Thread__bootstrap', '_Thread__bootstrap_inner', '_Thread__delete', '_Thread__exc_clear', '_Thread__exc_info',
'_Thread__initialized', '_Thread__stop', '__class__', '__delattr__', '__dict__', '__doc__', '__format__', '__getattribute__', '__hash__', '__init__', '__module__', '__new__', '__reduce__', '__reduce_ex__', '__repr__',
'__setattr__', '__sizeof__', '__str__', '__subclasshook__', '__weakref__', '_block', '_note', '_reset_internal_locks', '_set_daemon', '_set_ident', 'daemon', 'getName', 'ident', 'isAlive', 'isDaemon',
'is_alive', 'join', 'name', 'run', 'setDaemon', 'setName', 'start'
e.g. –

import threading
import time
exitFlag = 0
# inherit from threading.Thread class
class AvaneeshThread (threading.Thread):
def __init__(self, threadID, name, counter):
threading.Thread.__init__(self)
self.threadID = threadID
self.name = name
self.counter = counter

# override the run() method
def run(self):
print "Starting " + self.name
print_time(self.name, self.counter, 5)
print "Exiting " + self.name

# thread functionality method
def print_time(threadName, delay, counter):
while counter:
if exitFlag:
thread.exit()
time.sleep(delay)
print "%s: %s" % (threadName, time.ctime(time.time()))
counter -= 1

# Create new threads
thread1 = AvaneeshThread (1, "Thread-1", 1)
thread2 = AvaneeshThread (2, "Thread-2", 2)
# Start new Threads
thread1.start()
thread2.start()
print "Exiting Main Thread"

o/p -
Starting Thread-1
Starting Thread-2
Exiting Main Thread
Thread-1: Thu Mar 21 09:10:03 2013
Thread-1: Thu Mar 21 09:10:04 2013
Thread-2: Thu Mar 21 09:10:04 2013
Thread-1: Thu Mar 21 09:10:05 2013
Thread-1: Thu Mar 21 09:10:06 2013
Thread-2: Thu Mar 21 09:10:06 2013
Thread-1: Thu Mar 21 09:10:07 2013
Exiting Thread-1
Thread-2: Thu Mar 21 09:10:08 2013
Thread-2: Thu Mar 21 09:10:10 2013
Thread-2: Thu Mar 21 09:10:12 2013
Exiting Thread-2
Synchronization –
Need?
Available objects are - 'Event', 'Lock', 'RLock', 'Semaphore'

1. LOCK -
import threading
import time
class AvaneeshThread(threading.Thread):
def __init__(self, threadID, name, counter):
threading.Thread.__init__(self)
self.threadID = threadID
self.name = name
self.counter = counter
def run(self):
print "Starting " + self.name
# Get lock to synchronize threads
threadLock.acquire()
print_time(self.name, self.counter, 3)
# Free lock to release next thread
threadLock.release()
def print_time(threadName, delay, counter):
while counter:
time.sleep(delay)
print "%s: %s" % (threadName, time.ctime(time.time()))
counter -= 1

threadLock = threading.Lock()


2. Semaphore –
Defined number of thread with accecc control mechanism.
maxconnections = 5
...
pool_sema = Semaphore(value=maxconnections)
pool_sema.acquire();

conn = connectdb();
... use connection ...
conn.close();
pool_sema.release();

3. RLock –
This is a special kind of Lock where a thread can utilise the Lock multiple times. So,
more than once acquire() and release() are called on the Lock.
This is used when recursive Lock.acquire() and Lock.Release() are called by a thread.
lock = threading.Lock()
lock.acquire()
lock.acquire() # the second acquire() will fail
lock = threading.RLock()
lock.acquire()
lock.acquire() # the second acquire() will not fail

4. Condition –
It denotes some state change and access of a thread can be controlled for
synchronisation.
# get the condition object
condition = threading.Condition()

#acquire the condition obj
condition.acquire()
# signal for any state change
condition.notify() # signal that a new item is available

# release the condition obj
condition.release()
Thread Pool / Queue -
Get a suitable datastructure like dict to hold worker threads created in advance for
any coming tasks.
e.g. – ATM applicaton
A priority system can be implemented and used with the thread pool functionalities.
e.g. –
Having priority field in customised thread class.
class AvaneeshThread(threading.Thread):
def __init__(self, threadID, name, counter, priority):
threading.Thread.__init__(self)
self.threadID = threadID
self.name = name
self.counter = counter
self.priority = priority

Friday, August 2, 2013

Python class sample code



Python is object oriented language with support to many OO concepts.
A very simple sample of class and member methods -

class MyClass:
def __init__(self, id):
self.id = id;

def showId(self):
print "Value of Id is :"+str(self.id);
return;

def __del__(self):
print "Deleting the object...";

myCls = MyClass(10);
myCls.showId();
del myCls;

O/P -

Value of Id is :10
Deleting the object...

02-08-2013

Friday, July 12, 2013

Few Oracle SQL Performance Improvement Tips


Some of the performance improvement criteria for Oracle SQLS are below :

1. IN and NOT IN Operators -
These operators are slower than the operators EXISTS and NOT EXISTS.
Use EXISTS and NOT EXISTS with the target select statement.
This also gives chance for getting the index (if any) in the targetted sql utilised.
e.g. -
SELECT
BK.fm_book_id IN (select fm_book_id from fm_book_group_link where fm_group_id=128)
FROM BOOK BK

can be replace by

SELECT
BK.fm_book_id EXISTS (select fm_book_id from fm_book_group_link where fm_group_id=128)
FROM BOOK BK

2. LIKE operator -
Use leading character for pattern matching like 'A%' instead of '%A'.
Also, use TEXT field INDEX created and use CONTAINS in place of LIKE.
The entire story is at - http://www.orafaq.com/node/1918

3. Take care of system functions -
Try to avoid using system function as they can add up to the performance of the processing.

4. Ordering of the conditions in WHERE clause -
Ordering of the conditional statements in WHERE clause affects the table scan effort and impacts performance.
e.g. -
Use the statements having number (constant) comparison first, as this will filter the number of records and reduce the table scan.

Hope this will benefit somewhere :) Good Luck !

Avaneesh S. Tiwari
12-07-2013

Friday, January 22, 2010

Operator overloading

C++ supports Polymorphism concept with giving different & sepcial behaviour depending upon the context. Generally, this polymorphic behaviour is at compile time or at runtime.
Function overloading & operator overloading are two compile time polymorphism examples.
For this article, we will get an introduction to Operator overloading.

Opearator Overloading -

The existing supported operators are extended for their functionalities ( behaviour ) by operator overloading. This supports the extensibility concept of C++ which has made it to produce great amount of customised libraries.
Operator overloading adds up to the functionalities of the operator with preserving other features like presedence, number of arguments to be operated & basic functionality etc.


Prototype -

return_type operator op (argument list )
{
...
}
op - the operator to be loaded

The keyword "operator" is used for denoting the function as operator overloading function.
The function can not be static. But it can be made friend function.

Limitations -

There are operators which can not be supported for overloading as an exception -
a. Scope resolution operator (::)
b. size of operator (sizeof())
c. conditional operator (?:)
d. pointer to member variable (.*)

Also, when we make the function as friedn function, it can not overload the following operators -
a. =
b. ()
c. []
d. ->


Usability -
Its used for extensibility, reusability with additional features.

Example -

// code of Test2.hpp file

#include
#include

using namespace std;

template
class MyList : public std::list
{

public:

// Default ctor
MyList ( ) : std::list ( ) { };
MyList (size_t n) : std::list (n) { };
MyList (size_t n, const T& val) : std::list (n, val) { };

// overloading operator "[]" as member function
// returns the ith element from the list
const T& operator [] ( size_t i) const
{
typename std::list::const_iterator c_it=this->begin ( );
typename std::list::const_iterator cv_end=this->end ( );

size_t intCnt = 0;

// loop till ith element
while ( intCnt != i && c_it != cv_end )
{
c_it++ ;
intCnt++;
}

// return the ith element value
return *c_it;
}
};


// code of Test2.cpp file


#include "stdafx.h"
#include "Test2.h"

int main(int argc, char* argv[])
{
// instantiate the class MyList for string type values
MyList obj;
//add values
obj.push_back("Avaneesh");
obj.push_back("Anand");
obj.push_back("Amar");

//get the first element
std::cout< //get the second element
std::cout< //get the third element
std::cout<
return 0;
}

Wednesday, May 6, 2009

Pass by Reference in C++

Always try to pass objects by reference in C++ in funcation calls as it offers following advantages -

1. Efficient -
Pass by refernce just uses aliases for the object being passed. It does not make copy of the object.

2. Safe -
As reference variable is used for passing the object, possibility of NULL value is avoided.

3. Multiple value return -
Using the reference variable, one can make changes to the members of the object and return as a reference object. Thus, many changed values can be returned.

Wednesday, January 7, 2009

Embedding SQL into Unix Script

Embedding of SQL query in Unix Script -


The automation usability of the Unix Scripting can be enhanced with embedding the SQL queries into a Unix script file.
It can be achieved as mentioned in the below examples -

1.
isql -S -U -P << EOF

EOF

Use isql command with the aforesaid options.
<< EOF says, do the execution of the embedded sql after this command line till word "EOF" is encountered.

The output would be displayed on command prompt only.


2. isql -S -U -P << EOF >analytics_result.txt

EOF


Same as above with one addition , the output can bbe redirected to a file with indirection ">". Here the output file is "analytics_result.txt"


3.
isql -S -U -P -i analytics_query.sql << EOF
EOF


In case of big queries or multiple query execution, all sql stuffs could be packaged into a sql file and the file path could be mentioned with the option "-i".


Scope -

This automation could be used for database functionalities and running database queries as a scheduled job.




Avaneesh
07-01-2009

Tuesday, December 2, 2008

Dymanic cast

It is basically used for the safe type casting of base and derived classes.
Type casting from base class pointer to a derived class pointer is safe and does not require explicit casting, however reverse is not that much simple.
Type casting is required when we are pointing a base class object by a derived class pointer.
dynamic_cast is used for this type of herirachical casting ( upcasting ).
One pre requisite with this cast is - The base class should be polymorphic i.e. base class must have at least one virtual method.

In below example - Comment and comment out the virtual method of class A and check out the results.

#include "stdafx.h"
#include


class A
{
public :
A()
{
cout<<"A::A()"<}
~A()
{
cout<<"A::~A()"<}
//void virtual Test() {};
};


class B :public A
{
public :
B()
{
cout<<"B::B()"<}
~B()
{
cout<<"B::~B()"<}
};
int main(int argc, char* argv[])
{
try
{
A *objA = new A();
B *objB = new B();
objB = dynamic_cast(objA);
}
catch(...)
{
cout<<"error";
}
return 0;
}

Friday, October 3, 2008

Table Name Search for a Column

There could be situations when we need to know all the table names in our database which contain a required column name.The below stored procedure could be of use -
If exists ( select * from sysobjects where name

like 'GetTableName' and type = 'P'

)

BEGIN

DROP procedure GetTableName

END

GO

Create procedure GetTableName

@strString varchar(100)

As

Begin

Select name from sysobjects

where id in ( Select id from syscolumns where name like @strString )

End

GO

Monday, September 8, 2008

REALIZATION

In object oriented programming (OOPS), REALIZATION is a kind of relationship between two classes where one class provides the template for all the functions to be used , while the other class actually provides the functionalities to the defined functions.

The class providing the template is known as “Supplier” class while the class providing the implementation is called as “Consumer” class.

This type of relationship is used in Interface based architecture or template based architecture.

In the given example the class “Account” is an interface class and it gets implemented by the class
“SavingAccount”.

In UML the same thing is denoted as









#include "stdafx.h"


// Supplier class or Interface class
class Account
{
private:


protected:
float fPrincipal, fInterest, fTime, fRate;
public:
virtual void SetPrincipal(float fPrincipal)=0;
virtual void SetTime(float fTime)=0;
virtual void SetRate(float fRate)=0;
virtual void CalculateInterest()=0;
virtual void ShowInterest()=0;
};


// Consumer class or Implementor class
class SavingAccount : public Account
{
private:


protected:

public:
void SetPrincipal(float fPrincipal);
void SetTime(float fTime);
void SetRate(float fRate);
void CalculateInterest();
void ShowInterest();

};

void SavingAccount::SetPrincipal(float fPrincipal)
{
this->fPrincipal = fPrincipal;
}

void SavingAccount::SetTime(float fTime)
{
this->fTime = fTime;
}

void SavingAccount::SetRate(float fRate)
{
this->fRate = fRate;
}

void SavingAccount::CalculateInterest()
{
fInterest = (fPrincipal * fTime * fRate ) / 100;
}

void SavingAccount::ShowInterest()
{
printf("Intereset is - %f", fInterest);
}

int main(int argc, char* argv[])
{
SavingAccount objSavAcc;

objSavAcc.SetPrincipal(10000);
objSavAcc.SetRate(5.9);
objSavAcc.SetTime(2);
objSavAcc.ShowInterest();

return 0;
}






























Friday, August 29, 2008

Clustered and non clustered index

Just to explain the main difference between Clustered and non clustered index with a simple example.

Clustered index makes data storage in a sorted order based on the key/s used for indexing, while non clustered index does not.

Just have a look to the below piece of T-SQL statements to remember this -


Clustered Index Example -


drop table Clustered_Table
Go

create table Clustered_Table
(
id int,

name varchar(100)
)
Go


--Create Clsutered Index
Create Clustered Index Clust_ind_id
on Clustered_Table(id)
GO


-- Insert few records
Insert into Clustered_Table Values (1, 'Avaneesh')
GO
Insert into Clustered_Table Values (5, 'Suresh')
GO
Insert into Clustered_Table Values (3, 'Dinesh')
GO
Insert into Clustered_Table Values (2, 'Mahesh')
GO
Insert into Clustered_Table Values (4, 'Vikash')
GO


O/P –


Id name
1 Avaneesh
2 Mahesh
3 Dinesh
4 Vikash
5 Suresh



Note the output is in sorted order.





Non Clustered Index Example -

drop table Non_Clustered_Table
Go
create table Non_Clustered_Table
(
id int,

name varchar(100)
)
Go


-- Create non clustered index
Create nonClustered Index test_Clust_ind1
on Non_Clustered_Table (id)
GO


-- Insert the records
Insert into Non_Clustered_Table Values (1, 'Avaneesh')
GO
Insert into Non_Clustered_Table Values (5, 'Suresh')
GO
Insert into Non_Clustered_Table Values (3, 'Dinesh')
GO
Insert into Non_Clustered_Table Values (2, 'Mahesh')
GO
Insert into Non_Clustered_Table Values (4, 'Vikash')
GO


-- get the records with non clustred index used
select * from Non_Clustered_Table



O/P –

Id Name
1 Avaneesh
5 Suresh
3 Dinesh
2 Mahesh
4 Vikash


Note the order of the records. Same as we had entered.

Hope it will help you somewhere.
Bye.

Monday, August 18, 2008

Façade pattern

Design patterns provide solutions to frequently occurring problems and also these patterns make the software efficient by suggesting effective ways.
FACADE is one the patterns which is commonly used.

What is Façade pattern ?
In this pattern the external access to a software system is made organized and efficient. A system containing no of sub systems (modules) can exposes many interfaces to the
external systems (clients ). Frequently for getting access to the required module, intelligence needs to be added at client side only. It requires internal knowledge of the
system being accessed and could make the client side little thick.
Facade pattern makes the system to expose only single interface i.e. point of contact and internally makes the decision about the redirection of the client request to the
correct module.

Advantages?
Thus the system access is more organized and easy for the client system.

The below example shows a Facade implementation. In this, there could be no of schemes in account system which have different formulae for interest rates. Depending upon the passed scheme code, correct scheme function is invoked to compute the interest rate.


#include "stdafx.h"
#include "iostream.h"

enum Scheme { A, B} ;

class SchemeA
{
public :

double GetInterest(float dbAmt, int intTenure)
{
return ( 0.02 * dbAmt / intTenure );
}
};


class SchemeB
{
public :

double GetInterest(float dbAmt, int intTenure)
{
return ( 0.03 * dbAmt / intTenure );
}
};

// Facade class with interface GetInterest(...)

class Facade
{
public:

double GetInterest(Scheme SchemeType, float dbAmt, int intTenure)
{

// decision making for reditrection of the client request
if (SchemeType == A)
{
SchemeA objA;

return (objA.GetInterest(dbAmt, intTenure));
}

if (SchemeType == B)
{
SchemeA objB;

return (objB.GetInterest( dbAmt, intTenure));
}

}
};


// client system for the above Facaded system
int main(int argc, char* argv[])
{
Facade objFacade;

// call to the Facade interface
cout<< objFacade.GetInterest(A, 5000, 14);
return 0;
}

Thursday, June 26, 2008

Query Execution Plan








Fig 1



Fig 2


Often in database programming, we face the issue of query optimization. Though the Database Management System (DBMS) has one component known as "Query Optimizer" which takes care of optimization but programmer himself needs to improve the query to get the results efficiently.
While query optimization, there should be some benchmark / indicator to show the efficiency of the query which can help the programmer to decide which part to look on for optimization.

SQL Server 2000 has one such feature know as "Query Execution Plan".
One more terminology needs to be explained before going into that.


Cost of query - It figures how much CPU and I/O the query utilises. An optimized query should take less cost. Using this factor queries are compared for efficiency.

Query Execution Plan -
It means the way the SQL Server runs our query, how it optimizes and what are the costs for different actions of a query.

One very simple example -

There are two tables -Test1 and Test2 with 2 columns id and name each.
Selection the ids and name from these 2 table using following query -

Select T1.id, T2.Name
from test1 T1, test2 T2
where
T1.id = T2.id

Using the Query execution Plan we can do analysis of the costs occurred for the actions inside the query -

Check Fig 1.
It says -

1. Table scan 40 % cost - For scanning the tables T1 and T2, it costs 40 % of the entire query.

2. Hash Matching - For matching the fetched records as per the where clause it takes
19 %.

3. Select 0 % - Finally selecting the records.

(Where does the remaining 1 % go? )


Lets add something to the query - Say sorting -

Select T1.id, T2.Name
from test1 T1, test2 T2
where
T1.id = T2.id
order by T1.id

Check Fig 2.
Now the result has -

Scanning - 36 % each

Hash matching - 17 %

Sorting - This is new and because of the order by clause. Takes 11 %.

Finally select action.

(Its correct as 100 % total appears)

That’s all for this from me. Now your suggestion and advice.


Bye.
Avaneesh S. Tiwari
26 June '08

Sunday, June 15, 2008

Dot net COM interoperability

"COM interoperability" a topic something important for a person coming from C++ / COM background to dot net world. Also a frequent question in dot net tech interviews -

I tried putting few test applications and knowing what it is.
In COM world the final output which we get is in the form of Typelibrary, a binary output.
While in dot net supported languages like C#, the output is know as Assembly, not binary but known as Intermediate Language (IL) output.

On a broad level, COM interoperability is transformation of these two different types of output files.
There could be 2 cases -

1. COM outputs to be used in dot net languages - We need to convert the TypeLibrary to assembly. It’s done by utility - TlbImp.exe - Type library import.

I never used this explicitly as there is simple option tab available while giving reference to COM dll in the dot net editor. It internally manages these all stuff of
Conversion.


2. Dot net dlls to be used in unmanaged environments - It requires conversion of Assembly to TypeLib. It could be done with - RegAsm.exe utility which stands for Register
assembly as Typelib. Honestly saying, I never required and used this.

This is what I could write, please share your experience.

Bye.
Avaneesh Tiwari

15-06-2008

Wednesday, June 11, 2008

Am beginner for non WINDOWS

After working for 4 years in WINDOWS world, I have got chance to work on non windows platform. With these tough days, as a beginner, I could share this much for now.

GNU -
GNU is an organization mainly in the area of Open Source software. Richard Stallman started it. It has been well known for the developments and distribution of tools, utilities, Applications etc. used in conjunction with Unix OS. GNU softwares are distributed with General Public License (GPL). Few applications / tools known to me -

1. GCC - Compiler used for languages like - C, C++, Objective C etc. Now the latest version is - 4.3.1. I am working on little older - 3.2.2 (February 05 release). It supports many languages as well as hardware platforms. With several setting, it can be customized and made to suit our business.

2. GDB - Debugger tool. With command line, it appeared tough for me to use as have migrated from Windows!

3. DDD - Something for my rescue. It uses GDB debugger and provides user interface to some extent. So its a user interface debugger for UNIX / Linux programmers.

Thats all for this article, please share your views.

-- By Avaneesh Tiwari

Thursday, June 5, 2008

A good begining

Friends,

Its a lovely day as I am starting my technical blog. I believe this journey will be a successful one.

-- Avaneesh Tiwari

05-06-2008