Right - no it won't. Why not? Simple: it compiles the SQL too early for you, so it rightly assumes that @COL is a variable, not a column name, and at run time it compares the
content of @COL against 'P' rather than using "the content of the column named by @COL".
You can do it - it's clumsy and dangerous because you have to have to concatenate the content of the variable together with the rest of the SQL into an string and execute that, which leaves you wide open to an SQL Injection problem and that could damage or destroy your database. I don;t recommend it.
Instead, check the content of @COL and execute the appropriate SELECT based on that.
IF @COL='d1'
SELECT COUNT(*) FROM bat.studentbatch sb
INNER JOIN bat.student_attendance sa ON sb.sid=sa.sid
INNER JOIN bat.batchmaster bm ON sb.batchid=bm.batchid
WHERE bm.facultyid = 151
AND bm.batchstatus !='Completed'
AND d1 ='P'
ELSE IF @COL='d2'
SELECT COUNT(*) FROM bat.studentbatch sb
INNER JOIN bat.student_attendance sa ON sb.sid=sa.sid
INNER JOIN bat.batchmaster bm ON sb.batchid=bm.batchid
WHERE bm.facultyid = 151
AND bm.batchstatus !='Completed'
AND d2 ='P'
...
ELSE
SELECT -1