diff --git a/cmake-build-debug/Testing/Temporary/LastTest.log b/cmake-build-debug/Testing/Temporary/LastTest.log
index a75d9dca0bcdadfbcceb0dae51cba0a612aec74d..d8e53ccb92808641d4052b250dcefcdb21ff0154 100644
--- a/cmake-build-debug/Testing/Temporary/LastTest.log
+++ b/cmake-build-debug/Testing/Temporary/LastTest.log
@@ -1,3 +1,3 @@
-Start testing: Jun 26 15:59 CST
+Start testing: Jun 26 21:48 CST
 ----------------------------------------------------------
-End testing: Jun 26 15:59 CST
+End testing: Jun 26 21:48 CST
diff --git a/include/frontend/BasicBlock.hh b/include/frontend/BasicBlock.hh
index c38358efb65b5995b139f75c55d4db1c1356b60b..b74cb457040c1c59f4dcb4c141b35d89812010af 100644
--- a/include/frontend/BasicBlock.hh
+++ b/include/frontend/BasicBlock.hh
@@ -22,7 +22,7 @@ public:
     void pushVar(Value *v) {
         vars.push_back(v);
     }
-    virtual void print() = 0;
+    virtual void print(std::ostream& out) = 0;
     virtual void clear() = 0;
     virtual ~BasicBlock(){}
 };
@@ -30,11 +30,11 @@ class NormalBlock:public BasicBlock{
 public:
     BasicBlock* nextBB = nullptr;
     NormalBlock(BasicBlock* parent,std::string func_name, int cnt) : BasicBlock(parent,func_name,cnt){}
-    void print() override final{
-        std::cout << name << std::endl;
+    void print(std::ostream& out) override final{
+        out << name << std::endl;
         for (size_t i = 0; i < ir.size(); ++i) {
             std::cout << "\t";
-            ir[i]->print();
+            ir[i]->print(out);
         }
     };
     void clear() override final{}
@@ -46,11 +46,11 @@ public:
     Value* val = nullptr;
     bool isAnd = false;
     CondBlock(BasicBlock* parent,std::string func_name,int cnt): BasicBlock(parent,func_name,cnt){}
-    void print() override final{
-        std::cout << name << std::endl;
+    void print(std::ostream& out) override final{
+        out << name << std::endl;
         for (size_t i = 0; i < ir.size(); ++i) {
             std::cout << "\t";
-            ir[i]->print();
+            ir[i]->print(out);
         }
     }
     void clear() override final{}
@@ -62,15 +62,15 @@ public:
     std::vector<BasicBlock*> elseStmt;
 
     SelectBlock(BasicBlock* parent,std::string func_name,int cnt) : BasicBlock(parent,func_name,cnt){}
-    void print() override final{
+    void print(std::ostream& out) override final{
         for (size_t i = 0; i < cond.size(); ++i) {
-            cond[i]->print();
+            cond[i]->print(out);
         }
         for (size_t i = 0; i < ifStmt.size(); ++i) {
-            ifStmt[i]->print();
+            ifStmt[i]->print(out);
         }
         for (size_t i = 0; i < elseStmt.size(); ++i) {
-            elseStmt[i]->print();
+            elseStmt[i]->print(out);
         }
     };
     void clear() override final{
@@ -118,12 +118,12 @@ public:
     std::vector<BasicBlock*> whileStmt;
 
     IterationBlock(BasicBlock* parent,std::string func_name,int cnt) : BasicBlock(parent,func_name,cnt){}
-    void print() override final{
+    void print(std::ostream& out) override final{
         for (size_t i = 0; i < cond.size(); ++i) {
-            cond[i]->print();
+            cond[i]->print(out);
         }
         for (size_t i = 0; i < whileStmt.size(); ++i) {
-            whileStmt[i]->print();
+            whileStmt[i]->print(out);
         }
     }
     void clear() override final{
diff --git a/include/frontend/Function.hh b/include/frontend/Function.hh
index fb60ad3d8c192ed6160bd0e8527a2334c6ffb063..6e470b285b9a7f4fde770729b356355e0279bdbd 100644
--- a/include/frontend/Function.hh
+++ b/include/frontend/Function.hh
@@ -46,19 +46,19 @@ public:
             }
         }
     }
-    inline void print() {
-        std::cout << "define ";
-        return_type->print();
-        std::cout << "@" << name << "(";
+    inline void print(std::ostream& out) {
+        out << "define ";
+        return_type->print(out);
+        out << "@" << name << "(";
         for (size_t i = 0; i < params.size(); ++i) {
-            params[i]->print();
+            params[i]->print(out);
             if (i != params.size() - 1){
-                std::cout << ",";
+                out << ",";
             }
         }
-        std::cout << ")" <<std::endl;
+        out << ")" <<std::endl;
         for (size_t i = 0; i < basicBlocks.size(); ++i) {
-            basicBlocks[i]->print();
+            basicBlocks[i]->print(out);
         }
     }
 };
diff --git a/include/frontend/Instruction.hh b/include/frontend/Instruction.hh
index 9a22f251c8d3ba697dc84c54a9c7a8dc786e67ec..ce8af4fff2bf2b5a646ff8c82a57240c964a2cb3 100644
--- a/include/frontend/Instruction.hh
+++ b/include/frontend/Instruction.hh
@@ -14,7 +14,7 @@ enum class OP{
 class Instruction{
 public:
     Instruction() {}
-    virtual void print() = 0;
+    virtual void print(std::ostream& out) = 0;
     virtual ~Instruction(){}
 };
 class AllocIIR:public Instruction{
@@ -30,12 +30,12 @@ public:
         this->arrayLen = arrayLen;
         this->v = v;
     }
-    void print() override final{
-        v->print();
-        std::cout << " = AllocaI";
+    void print(std::ostream& out) override final{
+        v->print(out);
+        out << " = AllocaI";
         if(isArray)
-            std::cout << "(" << arrayLen << ")";
-        std::cout << std::endl;
+            out << "(" << arrayLen << ")";
+        out << std::endl;
     }
 };
 class AllocFIR:public Instruction{
@@ -51,12 +51,12 @@ public:
         this->arrayLen = arrayLen;
         this->v = v;
     }
-    void print() override final{
-        v->print();
-        std::cout << " = AllocaF";
+    void print(std::ostream& out) override final{
+        v->print(out);
+        out << " = AllocaF";
         if(isArray)
-            std::cout << "(" << arrayLen << ")";
-        std::cout << std::endl;
+            out << "(" << arrayLen << ")";
+        out << std::endl;
     }
 };
 
@@ -68,11 +68,11 @@ public:
         this->v1 = v1;
         this->v2 = v2;
     }
-    void print() override final{
-        v1->print();
-        std::cout << " = LoadI ";
-        v2->print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        v1->print(out);
+        out << " = LoadI ";
+        v2->print(out);
+        out << std::endl;
     }
 };
 class LoadFIR:public Instruction{
@@ -83,11 +83,11 @@ public:
         this->v1 = v1;
         this->v2 = v2;
     }
-    void print() override final{
-        v1->print();
-        std::cout << " = LoadI ";
-        v2->print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        v1->print(out);
+        out << " = LoadI ";
+        v2->print(out);
+        out << std::endl;
     }
 };
 class StoreIIR:public Instruction{
@@ -96,12 +96,12 @@ public:
     Value* dst;
     TempVal src;
     StoreIIR(Value* dst,TempVal src):dst(dst),src(src){}
-    void print() override final{
-        std::cout << "StoreI ";
-        src.print();
-        std::cout << " ";
-        dst->print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        out << "StoreI ";
+        src.print(out);
+        out << " ";
+        dst->print(out);
+        out << std::endl;
     }
 };
 class StoreFIR:public Instruction{
@@ -110,12 +110,12 @@ public:
     Value* dst;
     TempVal src;
     StoreFIR(Value* dst,TempVal src):dst(dst),src(src){}
-    void print() override final{
-        std::cout << "StoreF ";
-        src.print();
-        std::cout << " ";
-        dst->print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        out << "StoreF ";
+        src.print(out);
+        out << " ";
+        dst->print(out);
+        out << std::endl;
     }
 };
 class CastInt2FloatIR:public Instruction{
@@ -126,11 +126,11 @@ public:
         this->v1 = v1;
         this->v2 = v2;
     }
-    void print() override final{
-        v1->print();
-        std::cout << " = CastInt2Float ";
-        v2->print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        v1->print(out);
+        out << " = CastInt2Float ";
+        v2->print(out);
+        out << std::endl;
     }
 };
 class CastFloat2IntIR:public Instruction{
@@ -141,11 +141,11 @@ public:
         this->v1 = v1;
         this->v2 = v2;
     }
-    void print() override final{
-        v1->print();
-        std::cout << " = CastFloat2Int ";
-        v2->print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        v1->print(out);
+        out << " = CastFloat2Int ";
+        v2->print(out);
+        out << std::endl;
     }
 };
 class ArithmeticIR:public Instruction{
@@ -154,116 +154,116 @@ public:
     TempVal left;
     TempVal right;
     ArithmeticIR(TempVal res,TempVal left,TempVal right) : res(res),left(left),right(right){}
-    virtual void print() = 0;
+    virtual void print(std::ostream& out) = 0;
     virtual ~ArithmeticIR(){}
 };
 class AddIIR:public ArithmeticIR{
 public:
     AddIIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = AddI ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = AddI ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class AddFIR:public ArithmeticIR{
 public:
     AddFIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = AddF ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = AddF ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 
 class SubIIR:public ArithmeticIR{
 public:
     SubIIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = SubI ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = SubI ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class SubFIR:public ArithmeticIR{
 public:
     SubFIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = SubF ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = SubF ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class MulIIR:public ArithmeticIR{
 public:
     MulIIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = MulI ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = MulI ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class MulFIR:public ArithmeticIR{
 public:
     MulFIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = MulF ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = MulF ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class DivIIR:public ArithmeticIR{
 public:
     DivIIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = DivI ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = DivI ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class DivFIR:public ArithmeticIR{
 public:
     DivFIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = DivF ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = DivF ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class ModIR:public ArithmeticIR{
 public:
     ModIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = Mod ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = Mod ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class UnaryIR:public Instruction{
@@ -272,175 +272,175 @@ public:
     TempVal v;
     OP op;
     UnaryIR(TempVal res,TempVal v,OP op): res(res), v(v), op(op){}
-    void print() override final{
-        res.print();
-        std::cout << " = ";
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = ";
         switch (op) {
             case OP::NEG:
-                std::cout << "NEG ";break;
+                out << "NEG ";break;
             case OP::NOT:
-                std::cout << "NOT ";break;
+                out << "NOT ";break;
         }
-        v.print();
-        std::cout << std::endl;
+        v.print(out);
+        out << std::endl;
     }
 };
 class LTIIR:public ArithmeticIR{
 public:
     LTIIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = LTI ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = LTI ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class LTFIR:public ArithmeticIR{
 public:
     LTFIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = LTF ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = LTF ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class LEIIR:public ArithmeticIR{
 public:
     LEIIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = LEI ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = LEI ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class LEFIR:public ArithmeticIR{
 public:
     LEFIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = LEF ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = LEF ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class GTIIR:public ArithmeticIR{
 public:
     GTIIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = GTI ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = GTI ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class GTFIR:public ArithmeticIR{
 public:
     GTFIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = GTF ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = GTF ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class GEIIR:public ArithmeticIR{
 public:
     GEIIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = GEI ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = GEI ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class GEFIR:public ArithmeticIR{
 public:
     GEFIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = GEF ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = GEF ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class EQUIIR:public ArithmeticIR{
 public:
     EQUIIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = EQUI ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = EQUI ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class EQUFIR:public ArithmeticIR{
 public:
     EQUFIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = EQUF ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = EQUF ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class NEIIR:public ArithmeticIR{
 public:
     NEIIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = NEI ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = NEI ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class NEFIR:public ArithmeticIR{
 public:
     NEFIR(TempVal res,TempVal left,TempVal right) : ArithmeticIR(res,left,right){}
-    void print() override final{
-        res.print();
-        std::cout << " = NEF ";
-        left.print();
-        std::cout << " ";
-        right.print();
-        std::cout << std::endl;
+    void print(std::ostream& out) override final{
+        res.print(out);
+        out << " = NEF ";
+        left.print(out);
+        out << " ";
+        right.print(out);
+        out << std::endl;
     }
 };
 class BreakIR:public Instruction{
 public:
     BreakIR(){};
-    void print() override final{
-        std::cout << "break" << std::endl;
+    void print(std::ostream& out) override final{
+        out << "break" << std::endl;
     }
 };
 class ContinueIR:public Instruction{
 public:
     ContinueIR(){};
-    void print() override final{
-        std::cout << "continue" << std::endl;
+    void print(std::ostream& out) override final{
+        out << "continue" << std::endl;
     }
 };
 class ReturnIR:public Instruction{
@@ -461,16 +461,16 @@ public:
         retFloat = val;
         useFloat = true;
     }
-    void print() override final{
-        std::cout << "ret ";
+    void print(std::ostream& out) override final{
+        out << "ret ";
         if (v) {
-            v->print();
+            v->print(out);
         }else if (useInt) {
-            std::cout << "int " << retInt;
+            out << "int " << retInt;
         }else if (useFloat){
-            std::cout << "float " << retFloat;
+            out << "float " << retFloat;
         }
-        std::cout << "\n";
+        out << "\n";
     }
 };
 #include "BasicBlock.hh"
@@ -478,10 +478,10 @@ class JumpIR:public Instruction{
 public:
     BasicBlock* target;
     JumpIR(BasicBlock* target) : target(target){}
-    void print() override final{
-        std::cout << "goto ";
-        std::cout << target->name;
-        std::cout << "\n";
+    void print(std::ostream& out) override final{
+        out << "goto ";
+        out << target->name;
+        out << "\n";
     }
 };
 class BranchIR:public Instruction{
@@ -491,18 +491,18 @@ public:
     Value* cond;
     BranchIR(BasicBlock* trueTarget,BasicBlock* falseTarget,Value* cond) :
     trueTarget(trueTarget),falseTarget(falseTarget),cond(cond) {}
-    void print() override final{
-        std::cout << "goto ";
-        cond->print();
-        std::cout << " ? ";
+    void print(std::ostream& out) override final{
+        out << "goto ";
+        cond->print(out);
+        out << " ? ";
         if(trueTarget) {
-            std::cout << trueTarget->name;
+            out << trueTarget->name;
         }
-        std::cout << " : ";
+        out << " : ";
         if(falseTarget) {
-            std::cout << falseTarget->name;
+            out << falseTarget->name;
         }
-        std::cout << "\n";
+        out << "\n";
     }
 };
 class GEPIR:public Instruction{
@@ -521,16 +521,16 @@ public:
         this->v2 = v2;
         this->arrayLen = arrayLen;
     }
-    void print() override final{
-        v1->print();
-        std::cout << " = GEP ";
-        v2->print();
+    void print(std::ostream& out) override final{
+        v1->print(out);
+        out << " = GEP ";
+        v2->print(out);
         if(v3) {
-            std::cout << " ";
-            v3->print();
-            std::cout << std::endl;
+            out << " ";
+            v3->print(out);
+            out << std::endl;
         }else {
-            std::cout << " " << arrayLen << std::endl;
+            out << " " << arrayLen << std::endl;
         }
     };
 };
@@ -549,26 +549,26 @@ public:
         this->args = args;
         this->returnVal = v;
     }
-    void print() override final{
+    void print(std::ostream& out) override final{
         if (returnVal) {
-            returnVal->print();
-            std::cout << " = ";
+            returnVal->print(out);
+            out << " = ";
         }
-        std::cout << "call " << func->name << "(";
+        out << "call " << func->name << "(";
         for (size_t i = 0; i < args.size(); ++i) {
             if(args[i].getVal()) {
-                args[i].getVal()->print();
+                args[i].getVal()->print(out);
             }else {
                 if(args[i].isInt()) {
-                    std::cout << args[i].getInt();
+                    out << args[i].getInt();
                 }else {
-                    std::cout << args[i].getFloat();
+                    out << args[i].getFloat();
                 }
             }
             if (i < args.size() - 1) {
-                std::cout << " , ";
+                out << " , ";
             }else {
-                std::cout << ")\n";
+                out << ")\n";
             }
         }
     }
diff --git a/include/frontend/IrVisitor.hh b/include/frontend/IrVisitor.hh
index 9cc7a754bef7c39d9046fdcee8f5cbb3212b134c..61646da73fe6999f4a208d6f09cba23569b683e8 100644
--- a/include/frontend/IrVisitor.hh
+++ b/include/frontend/IrVisitor.hh
@@ -58,17 +58,17 @@ public:
         var->setGlobal(true);
         globalVars.push_back(var);
     }
-    void print() {
-        std::cout << "globalVars:" << std::endl;
+    void print(std::ostream& out = std::cout) {
+        out << "globalVars:" << std::endl;
         for (size_t i = 0; i < globalVars.size(); ++i) {
-            std::cout << "\t";
-            globalVars[i]->print();
-            std::cout << std::endl;
+            out << "\t";
+            globalVars[i]->print(out);
+            out << std::endl;
         }
-        std::cout << ".entryBB:" << std::endl;
+        out << ".entryBB:" << std::endl;
         entry->print();
         for (size_t i = 0; i < functions.size(); ++i) {
-            functions[i]->print();
+            functions[i]->print(out);
         }
     }
     //Created by lin 5.22
diff --git a/include/frontend/Value.hh b/include/frontend/Value.hh
index 150e3dfc1a70f762670f7694b603a84d83b566bd..ce2f26946582384167db09842317f39177bd6825 100644
--- a/include/frontend/Value.hh
+++ b/include/frontend/Value.hh
@@ -39,20 +39,20 @@ public:
     Type* getContained() {
         return contained;
     }
-    void print() {
+    void print(std::ostream& out) {
         switch (tid) {
             case INT:
-                std::cout << "int";
+                out << "int";
                 break;
             case FLOAT:
-                std::cout << "float";
+                out << "float";
                 break;
             case VOID:
-                std::cout << "void";
+                out << "void";
                 break;
             case POINTER:
-                contained->print();
-                std::cout << "*";
+                contained->print(out);
+                out << "*";
         }
     }
 private:
@@ -64,7 +64,7 @@ class Value{
 public:
     Value(){}
     virtual ~Value(){}
-    virtual void print() = 0;
+    virtual void print(std::ostream& out) = 0;
     bool is_Array() {return isArray;}
     void setArray(bool flag) {isArray = flag;}
     void setArrayDims(std::vector<int> arrDims) {arrayDims = arrDims;}
@@ -101,13 +101,13 @@ public:
         this->type = type;
         this->isGlobal = isGlobal;
     }
-    void print() override final {
+    void print(std::ostream& out = std::cout) override final {
         if (isGlobal){
-            type->print();
-            std::cout << " @" << name;
+            type->print(out);
+            out << " @" << name;
         }else {
-            type->print();
-            std::cout << " @" << num;
+            type->print(out);
+            out << " @" << num;
         }
     }
     void push() {
@@ -121,11 +121,11 @@ private:
     Value* val;
     Type* type;
 public:
-    void print() {
+    void print(std::ostream& out) {
         if (val) {
-            val->print();
+            val->print(out);
         } else {
-            std::cout << getConst();
+            out << getConst();
         }
     }
     bool isInt() {return type->isInt();}
@@ -244,28 +244,28 @@ public:
         this->type = type;
         this->isGlobal = isGlobal;
     }
-    void print() override final {
+    void print(std::ostream& out) override final {
         if(!isArray)
         {
-            std::cout << "const ";
-            type->print();
+            out << "const ";
+            type->print(out);
             std::cout << " @" <<name;
             if (type->isInt()) {
-                std::cout << " = " <<intVal;
+                out << " = " <<intVal;
             }else{
-                std::cout << " = " << floatVal;
+                out << " = " << floatVal;
             }
         }
         else
         {
             if (isGlobal){
-                std::cout << "const ";
-                type->print();
-                std::cout << " @" << name;
+                out << "const ";
+                type->print(out);
+                out << " @" << name;
             }else {
-                std::cout << "const ";
-                type->print();
-                std::cout << " @" << num;
+                out << "const ";
+                type->print(out);
+                out << " @" << num;
             }
         }
 
diff --git a/main.cpp b/main.cpp
index dc498335ed0f7c0194a3f2a2fc44edf5b5e09f20..7bf13ed831465f984ac6e6f69fc81c225654f1d6 100644
--- a/main.cpp
+++ b/main.cpp
@@ -22,7 +22,7 @@ int main (int argc, char *argv[])
         std::cerr << "error: " << e.what() << "\n";
         return EXIT_FAILURE;
     }
-    irVisitor.print();
+    irVisitor.print(std::cout);
     std::cout << "end..." <<std::endl;
     return 0;
 }
\ No newline at end of file