// File: /workspace/github_cpp_makefile_star2_O2/hkbu-victor[P]SFastLDA/super_fast_final1_w.cpp
// Function: main
int main(int argc, char **argv){
  	char line[ 80 ];
    int n, i, j, docId, wordId, count;
    FILE *fr;

    parse_args(argc, argv);

    square_limit = -1;
    printf("\nFinal Sparse word-by-word: Opening and reading dataset file...\n");

    D = 0; W = 0; nTokens = 0;
    fr = fopen(dFile,"rt");
    if (fr == NULL){
       	printf("\n\nCannot find the UCI bag-of-words format input corpus file %s !!!\n\n\n", dFile);
       	exit(1);
    }
    fgets(line, 80, fr);
    sscanf(line, "%d", &D);
    fgets(line, 80, fr);
    sscanf(line, "%d", &W);
    fgets(line, 80, fr);

    int lineNo = 3;

    while (fgets(line, 80, fr) != NULL){
      	sscanf( line, "%d %d %d", &docId, &wordId, &count);
      	lineNo++;
      	nTokens += count;
      	if ((lineNo % 2000000) == 0)
			printf("first parse : processing line %d \n", lineNo);
    }
    printf("\nTotal documents: %d, Vocab Size : %d, Num. Tokens : %d\n", D, W, nTokens);

    //allocate memory
    d = (int *) calloc(nTokens, sizeof(int));
    w = (int *) calloc(nTokens, sizeof(int));
    z = (int *) calloc(nTokens, sizeof(int));
    doc_lens = (int *) calloc(D, sizeof(int));
    word_lens = (int *) calloc(W, sizeof(int));

    rewind(fr);

    fgets(line, 80, fr); fgets(line, 80, fr); fgets(line, 80, fr);
    lineNo = 3;
    n = 0;
    while (fgets(line, 80, fr) != NULL){
    	sscanf( line, "%d %d %d", &docId, &wordId, &count);
    	lineNo++;
    	doc_lens[ docId-1 ] += count;
    	word_lens[ wordId-1 ] += count;
    	for (i=0; i<count; i++){
    		d[n] = docId - 1;
    		w[n] = wordId - 1;
    		n++;
    	}
    	if ((lineNo % 1000000) == 0)
    		printf("second parse : processing line %d \n", lineNo);
    }
    fclose(fr);

    for (i=0; i<W; i++){
    	if (word_lens[i] > square_limit)
    		square_limit = word_lens[i];
    }

    printf( "Arguments:\n" );
    printf( "\tNumber of words      W = %d\n"    , W );
    printf( "\tNumber of docs       D = %d\n"    , D );
    printf( "\tNumber of topics     T = %d\n"    , T );
    printf( "\tNumber of iterations N = %d\n"    , NN );
    printf( "\tHyperparameter   ALPHA = %4.4f\n" , argALPHA );
    printf( "\tHyperparameter    BETA = %4.4f\n" , BETA );
    printf( "\tSeed number            = %d\n"    , SEED );
    printf( "\tNumber of tokens       = %d\n"    , nTokens );
    printf( "\tSquare Limit           = %d\n"    , square_limit);

    if (oFile != NULL){
    	printf("\n\tOutput file: %s.\n\n", oFile);
    }else{
    	printf("\n\tNo output file specified.\n\n");
    }


    ztot = new int[T]; std::fill_n(ztot, T, 0);
    ALPHA = new double[T]; std::fill_n(ALPHA, T, argALPHA);
    BETA_D_2_norm = new double[D];	//summation over topics of ALPHA*wi
    D_pair_count = new int[D]; std::fill_n(D_pair_count, D, 0);
    W_pair_count = new int[W]; std::fill_n(W_pair_count, W, 0);
    pivotal_topic_indexes = new int[T];
    pivotal_topic_values = new double[T];
    d_pivotal_topic_indexes = new int[T];
    d_pivotal_topic_values = new double[T];
    common_topic_pos = new int[T];
    ONE_OVER_Z = new double[T];
    square_increment = new long[square_limit];
    square_decrement = new long[square_limit];
    square_of = new long[square_limit];
    wi_array = new int[T];
    wi_index_to_pos = new int[T];

    wpIdx = new W_DoublePair*[W];
    wpVal = new int*[W];
    for (i=0; i<W; i++){
   		wpIdx[i] = new W_DoublePair[T];
    	wpVal[i] = new int[T];
    	for (j=0; j<T; j++){
    		wpIdx[i][j].index = -1;
    	}
		std::fill_n(wpVal[i], T, 0);
    }

    dpPair = new D_DoublePair*[D];
    for (i=0; i<D; i++){
    	if (doc_lens[i] < T){
        	dpPair[i] = new D_DoublePair[doc_lens[i]];
        	di_pair = dpPair[i];
    		for (j=0; j<doc_lens[i]; j++){
    			di_pair[j].index = -1;
    			di_pair[j].value = 0;
    		}
    	}else{
        	dpPair[i] = new D_DoublePair[T];
        	di_pair = dpPair[i];
    		for (j=0; j<T; j++){
    			di_pair[j].index = -1;
    			di_pair[j].value = 0;
    		}
    	}
    }

    std::fill_n(wi_index_to_pos, T, -1);

    GibbsSamplerLDA();

    if (oFile != NULL){
    	export_results(oFile);
    	printf("\nOutput file is written to %s", oFile);
    }

    printf("\nFinished !!!\n");
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x68, %rsp
callq 0x1325
orl $-0x1, 0x46eb(%rip)     # 0x7124
leaq 0x1b70(%rip), %rdi      # 0x45b0
callq 0x1130
andl $0x0, 0x46c0(%rip)      # 0x710c
andl $0x0, 0x46bd(%rip)      # 0x7110
andl $0x0, 0x46c6(%rip)      # 0x7120
movq 0x4677(%rip), %rdi      # 0x70d8
leaq 0x1679(%rip), %rsi      # 0x40e1
callq 0x10e0
testq %rax, %rax
je 0x31fd
movq %rax, %rbx
leaq 0x10(%rsp), %r14
pushq $0x50
popq %rbp
movq %r14, %rdi
movl %ebp, %esi
movq %rax, %rdx
callq 0x1150
leaq 0x169b(%rip), %r15      # 0x4130
leaq 0x4670(%rip), %rdx      # 0x710c
movq %r14, %rdi
movq %r15, %rsi
xorl %eax, %eax
callq 0x10c0
movq %r14, %rdi
movl %ebp, %esi
movq %rbx, %rdx
callq 0x1150
leaq 0x4653(%rip), %rdx      # 0x7110
movq %r14, %rdi
movq %r15, %rsi
xorl %eax, %eax
callq 0x10c0
movq %r14, %rdi
movl %ebp, %esi
movq %rbx, %rdx
callq 0x1150
pushq $-0x4
popq %rbp
pushq $0x4
popq %r15
movq %rsp, %r12
movl %r15d, %eax
xorl %edx, %edx
movl $0x1e8480, %ecx         # imm = 0x1E8480
divl %ecx
movl %eax, %r13d
movq %r14, %rdi
pushq $0x50
popq %rsi
movq %rbx, %rdx
callq 0x1150
testq %rax, %rax
je 0x2b51
imull $0x1e8480, %r13d, %r13d # imm = 0x1E8480
addl %ebp, %r13d
movq %r14, %rdi
leaq 0x1613(%rip), %rsi      # 0x412a
leaq 0xc(%rsp), %rdx
leaq 0x8(%rsp), %rcx
movq %r12, %r8
xorl %eax, %eax
callq 0x10c0
movl (%rsp), %eax
addl %eax, 0x45ec(%rip)      # 0x7120
testl %r13d, %r13d
jne 0x2b4a
leaq 0x15f3(%rip), %rdi      # 0x4133
movl %r15d, %esi
xorl %eax, %eax
callq 0x1040
decl %ebp
incl %r15d
jmp 0x2ae1
movl 0x45b5(%rip), %esi      # 0x710c
movl 0x45b3(%rip), %edx      # 0x7110
movl 0x45bd(%rip), %ecx      # 0x7120
leaq 0x15ec(%rip), %rdi      # 0x4156
xorl %eax, %eax
callq 0x1040
movslq 0x45a8(%rip), %r15      # 0x7120
pushq $0x4
popq %r14
movq %r15, %rdi
movq %r14, %rsi
callq 0x1070
movq %rax, 0x45ba(%rip)      # 0x7148
movq %r15, %rdi
movq %r14, %rsi
callq 0x1070
movq %rax, 0x45b0(%rip)      # 0x7150
movq %r15, %rdi
movq %r14, %rsi
callq 0x1070
movq %rax, 0x45a6(%rip)      # 0x7158
movslq 0x4553(%rip), %rdi      # 0x710c
movq %r14, %rsi
callq 0x1070
movq %rax, 0x4598(%rip)      # 0x7160
movslq 0x4541(%rip), %rdi      # 0x7110
movq %r14, %rsi
callq 0x1070
movq %rax, 0x458a(%rip)      # 0x7168
movq %rbx, %rdi
callq 0x1050
leaq 0x10(%rsp), %r14
pushq $0x50
popq %rbp
movq %r14, %rdi
movl %ebp, %esi
movq %rbx, %rdx
callq 0x1150
movq %r14, %rdi
movl %ebp, %esi
movq %rbx, %rdx
callq 0x1150
movq %r14, %rdi
movl %ebp, %esi
movq %rbx, %rdx
callq 0x1150
pushq $0x3
popq %r15
movq %rsp, %r12
movl $0xf4240, %r13d         # imm = 0xF4240
xorl %ebp, %ebp
movq %r14, %rdi
pushq $0x50
popq %rsi
movq %rbx, %rdx
callq 0x1150
testq %rax, %rax
je 0x2ce5
movq %r14, %rdi
leaq 0x14e5(%rip), %rsi      # 0x412a
leaq 0xc(%rsp), %rdx
leaq 0x8(%rsp), %rcx
movq %r12, %r8
xorl %eax, %eax
callq 0x10c0
movl (%rsp), %eax
movq 0x44fd(%rip), %rcx      # 0x7160
movslq 0xc(%rsp), %rdx
addl %eax, -0x4(%rcx,%rdx,4)
movl (%rsp), %eax
movq 0x44f2(%rip), %rcx      # 0x7168
movslq 0x8(%rsp), %rdx
addl %eax, -0x4(%rcx,%rdx,4)
movslq %ebp, %rbp
leaq (,%rbp,4), %rax
movq 0x44b7(%rip), %rdx      # 0x7148
addq %rax, %rdx
addq 0x44b5(%rip), %rax      # 0x7150
xorl %ecx, %ecx
cmpl (%rsp), %ecx
jge 0x2cb9
movl 0xc(%rsp), %esi
decl %esi
movl %esi, (%rdx,%rcx,4)
movl 0x8(%rsp), %esi
decl %esi
movl %esi, (%rax,%rcx,4)
incq %rcx
jmp 0x2c9d
incl %r15d
movl %r15d, %eax
xorl %edx, %edx
divl %r13d
addq %rcx, %rbp
testl %edx, %edx
jne 0x2c24
leaq 0x14b9(%rip), %rdi      # 0x418f
movl %r15d, %esi
xorl %eax, %eax
callq 0x1040
jmp 0x2c24
movq %rbx, %rdi
callq 0x10d0
movl 0x441d(%rip), %eax      # 0x7110
movl 0x442b(%rip), %esi      # 0x7124
movq 0x4468(%rip), %rcx      # 0x7168
xorl %edx, %edx
testl %eax, %eax
cmovlel %edx, %eax
cmpq %rdx, %rax
je 0x2d20
movl (%rcx,%rdx,4), %edi
cmpl %esi, %edi
jle 0x2d1b
movl %edi, 0x440b(%rip)      # 0x7124
movl %edi, %esi
incq %rdx
jmp 0x2d07
leaq 0x18c9(%rip), %rdi      # 0x45f0
callq 0x1130
movl 0x43de(%rip), %esi      # 0x7110
leaq 0x147a(%rip), %rdi      # 0x41b3
xorl %eax, %eax
callq 0x1040
movl 0x43c6(%rip), %esi      # 0x710c
leaq 0x1484(%rip), %rdi      # 0x41d1
xorl %eax, %eax
callq 0x1040
movl 0x43a6(%rip), %esi      # 0x7100
leaq 0x148e(%rip), %rdi      # 0x41ef
xorl %eax, %eax
callq 0x1040
movl 0x4396(%rip), %esi      # 0x7104
leaq 0x1498(%rip), %rdi      # 0x420d
xorl %eax, %eax
callq 0x1040
movsd 0x43fc(%rip), %xmm0     # 0x7180
leaq 0x14a0(%rip), %rdi      # 0x422b
movb $0x1, %al
callq 0x1040
movsd 0x43ee(%rip), %xmm0     # 0x7188
leaq 0x14ab(%rip), %rdi      # 0x424c
movb $0x1, %al
callq 0x1040
movl 0x435a(%rip), %esi      # 0x7108
leaq 0x14b8(%rip), %rdi      # 0x426d
xorl %eax, %eax
callq 0x1040
movl 0x435e(%rip), %esi      # 0x7120
leaq 0x14c2(%rip), %rdi      # 0x428b
xorl %eax, %eax
callq 0x1040
movl 0x434e(%rip), %esi      # 0x7124
leaq 0x14cc(%rip), %rdi      # 0x42a9
xorl %eax, %eax
callq 0x1040
movq 0x42f5(%rip), %rsi      # 0x70e0
testq %rsi, %rsi
je 0x2e00
leaq 0x14d0(%rip), %rdi      # 0x42c7
xorl %eax, %eax
callq 0x1040
jmp 0x2e0c
leaq 0x17f4(%rip), %rdi      # 0x45fb
callq 0x1130
movslq 0x42ed(%rip), %r14      # 0x7100
leaq (,%r14,4), %rdi
testq %r14, %r14
pushq $-0x1
popq %r12
cmovsq %r12, %rdi
callq 0x1030
movq %rax, 0x42f6(%rip)      # 0x7128
leaq 0x4(%rsp), %rbx
andl $0x0, (%rbx)
movq %rax, %rdi
movl %r14d, %esi
movq %rbx, %rdx
callq 0x3677
movslq 0x42b1(%rip), %r14      # 0x7100
leaq (,%r14,8), %rdi
testq %r14, %r14
cmovsq %r12, %rdi
callq 0x1030
movq %rax, 0x433e(%rip)      # 0x71a8
leaq 0x430f(%rip), %rdx      # 0x7180
movq %rax, %rdi
movl %r14d, %esi
callq 0x3afc
movslq 0x4289(%rip), %r14      # 0x710c
leaq (,%r14,8), %rdi
testq %r14, %r14
cmovsq %r12, %rdi
leaq (,%r14,4), %r15
cmovsq %r12, %r15
callq 0x1030
movq %rax, 0x431e(%rip)      # 0x71c8
movq %r15, %rdi
callq 0x1030
movq %rax, 0x42b7(%rip)      # 0x7170
andl $0x0, (%rbx)
leaq 0x4(%rsp), %r15
movq %rax, %rdi
movl %r14d, %esi
movq %r15, %rdx
callq 0x3677
movslq 0x423a(%rip), %r14      # 0x7110
leaq (,%r14,4), %rdi
testq %r14, %r14
cmovsq %r12, %rdi
callq 0x1030
movq %rax, 0x4287(%rip)      # 0x7178
andl $0x0, (%r15)
leaq 0x4(%rsp), %rdx
movq %rax, %rdi
movl %r14d, %esi
callq 0x3677
movslq 0x41f4(%rip), %rax      # 0x7100
leaq (,%rax,4), %r14
testq %rax, %rax
cmovsq %r12, %r14
leaq (,%rax,8), %r15
cmovsq %r12, %r15
movq %r14, %rdi
callq 0x1030
movq %rax, 0x41fa(%rip)      # 0x7130
movq %r15, %rdi
callq 0x1030
movq %rax, 0x426b(%rip)      # 0x71b0
movq %r14, %rdi
callq 0x1030
movq %rax, 0x41e4(%rip)      # 0x7138
movq %r15, %rdi
callq 0x1030
movq %rax, 0x4255(%rip)      # 0x71b8
movq %r14, %rdi
callq 0x1030
movq %rax, 0x41ce(%rip)      # 0x7140
movq %r15, %rdi
callq 0x1030
movq %rax, 0x423f(%rip)      # 0x71c0
movslq 0x419c(%rip), %rax      # 0x7124
leaq (,%rax,8), %r15
testq %rax, %rax
cmovsq %r12, %r15
movq %r15, %rdi
callq 0x1030
movq %rax, 0x4142(%rip)      # 0x70e8
movq %r15, %rdi
callq 0x1030
movq %rax, 0x413b(%rip)      # 0x70f0
movq %r15, %rdi
callq 0x1030
movq %rax, 0x4134(%rip)      # 0x70f8
movq %r14, %rdi
callq 0x1030
movq %rax, 0x420d(%rip)      # 0x71e0
movq %r14, %rdi
callq 0x1030
movq %rax, 0x4206(%rip)      # 0x71e8
movslq 0x4127(%rip), %r15      # 0x7110
leaq (,%r15,8), %r14
testq %r15, %r15
cmovsq %r12, %r14
movq %r14, %rdi
callq 0x1030
movq %rax, 0x4211(%rip)      # 0x7218
movq %r14, %rdi
callq 0x1030
movq %rax, 0x41c2(%rip)      # 0x71d8
xorl %r13d, %r13d
movslq %r15d, %rax
cmpq %rax, %r13
jge 0x30b9
movslq 0x40d4(%rip), %r14      # 0x7100
leaq (,%r14,8), %rdi
testq %r14, %r14
cmovsq %r12, %rdi
leaq (,%r14,4), %r15
cmovsq %r12, %r15
callq 0x1030
movq 0x41c5(%rip), %rcx      # 0x7218
movq %rax, (%rcx,%r13,8)
movq %r15, %rdi
callq 0x1030
movq 0x4172(%rip), %rcx      # 0x71d8
movq %rax, (%rcx,%r13,8)
movq 0x41a7(%rip), %rax      # 0x7218
xorl %ecx, %ecx
movslq %r14d, %rdx
cmpq %rdx, %rcx
jge 0x308f
movq (%rax,%r13,8), %rdx
orl $-0x1, (%rdx,%rcx,8)
incq %rcx
movl 0x4073(%rip), %r14d     # 0x7100
jmp 0x3073
movq 0x4142(%rip), %rax      # 0x71d8
movq (%rax,%r13,8), %rdi
andl $0x0, 0x4(%rsp)
movl %r14d, %esi
movq %rbx, %rdx
callq 0x3677
incq %r13
movl 0x405c(%rip), %r15d     # 0x7110
jmp 0x3019
movslq 0x404c(%rip), %r13      # 0x710c
leaq (,%r13,8), %rdi
testq %r13, %r13
cmovsq %r12, %rdi
callq 0x1030
movq %rax, %rbx
movq %rax, 0x414a(%rip)      # 0x7228
xorl %r14d, %r14d
movl $0xffffffff, %r15d      # imm = 0xFFFFFFFF
movslq %r13d, %rax
cmpq %rax, %r14
jge 0x319b
movq 0x4066(%rip), %rax      # 0x7160
movslq (%rax,%r14,4), %rax
movl 0x3ffc(%rip), %ebp      # 0x7100
cmpl %ebp, %eax
jge 0x314b
movq %rax, %rdi
shlq $0x3, %rdi
testl %eax, %eax
cmovsq %r12, %rdi
callq 0x1030
movq %rax, (%rbx,%r14,8)
movq 0x4103(%rip), %rbx      # 0x7228
movq (%rbx,%r14,8), %rax
movq %rax, 0x40f0(%rip)      # 0x7220
movq 0x4029(%rip), %rcx      # 0x7160
xorl %edx, %edx
movslq (%rcx,%r14,4), %rsi
cmpq %rsi, %rdx
jge 0x318c
movq %r15, (%rax,%rdx,8)
incq %rdx
jmp 0x3139
movslq %ebp, %rdi
shlq $0x3, %rdi
testl %ebp, %ebp
cmovsq %r12, %rdi
callq 0x1030
movq %rax, (%rbx,%r14,8)
movq 0x40c0(%rip), %rbx      # 0x7228
movq (%rbx,%r14,8), %rax
movq %rax, 0x40ad(%rip)      # 0x7220
xorl %ecx, %ecx
movslq %ebp, %rdx
cmpq %rdx, %rcx
jge 0x318c
movq %r15, (%rax,%rcx,8)
incq %rcx
movl 0x3f76(%rip), %ebp      # 0x7100
jmp 0x3175
incq %r14
movl 0x3f76(%rip), %r13d     # 0x710c
jmp 0x30e7
movq 0x4046(%rip), %rdi      # 0x71e8
movl 0x3f58(%rip), %esi      # 0x7100
leaq 0x4(%rsp), %rdx
orl $-0x1, (%rdx)
callq 0x3677
callq 0x19bc
movq 0x3f1f(%rip), %rdi      # 0x70e0
testq %rdi, %rdi
je 0x31e0
callq 0x14e3
movq 0x3f0e(%rip), %rsi      # 0x70e0
leaq 0x1103(%rip), %rdi      # 0x42dc
xorl %eax, %eax
callq 0x1040
leaq 0x1431(%rip), %rdi      # 0x4618
callq 0x1130
xorl %eax, %eax
addq $0x68, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
movq 0x3ed4(%rip), %rsi      # 0x70d8
leaq 0xed9(%rip), %rdi       # 0x40e4
xorl %eax, %eax
callq 0x1040
pushq $0x1
popq %rdi
callq 0x10f0