2012-04-15 2 views
0

Самообучение себя C++, и я знаю, что мне не хватает чего-то критического, но я не могу для жизни понять, что это такое.Строка становится пустой после find_last_of() и substr()?

Простите огромный блок кода, я был соблазн урезать его до критических элементов, но я решил, что если я оставил его нетронутым, вы люди могли бы иметь другие образовательные критические замечания о моем стиле кодирования ...

#include <stdio.h> 
#include <stdlib.h> 
#include <iostream> 
#include <sstream> 
#include <string> 
#include <vector> 
#include <fstream> 

using namespace std; 

// main routine 
int main(int argc, char *argv[]) { 
    // will store filetype here for later 
    string filetype = ""; 
    string filename; 

    // if no arguments, die. 
    if (argc < 2) { 
     cout << "ERROR: Nothing to do." << endl; 
     return 1; 
    } 

    // if more than one argument, die. 
    else if (argc > 2) { 
     // TODO: support for multiple files being checked would go here. 
     cout << "ERROR: Too many arguments." << endl; 
     return 1; 
    } 

    // otherwise, check filetype 
    else { 
     string filename = argv[1]; 
     cout << "Filename: " << filename << endl; 
     //searching from the end, find the extension of the filename 
     int dot = filename.find_last_of('.'); 
     if (dot == -1){ 
      // TODO: Add support for filenames with no extension 
      cout << "ERROR: Filename with no extension." << endl; 
      return 1; 
     } 
     string extension = filename.substr(dot); 
     if (extension == ".htm" || extension == ".html"){ 
      filetype = "html"; 
     } 
     else if (extension == ".c"){ 
      filetype = "c"; 
     } 
     else if (extension == ".c++" || extension == ".cpp") { 
      filetype = "cpp"; 
     } 
     else { 
      cout << "ERROR: unsupported file extension" << endl; 
      // TODO: try to guess filetype from file headers here 
     } 
    } 

    cout << "Determined filetype: " << filetype << endl; 
    cout << "Filename: " << filename << endl; 

    return 0; 
} 
              // All done :] 

Проблема, которую я испытываю, таинственна. Я положил аргумент, переданный в строку, как так:

string filename = argv[1]; 

, а затем поиск его расширения, начиная с конца и работать свой путь к началу:

int dot = filename.find_last_of('.'); 
string extension = filename.substr(dot); 

Это все работает, как ожидалось , но потом, когда я пытаюсь вывести имя файла, он загадочно пуст? Я попробовал отладку cout. Когда я распечатываю строку перед тем, как я ее просматриваю, она печатает правильно. После этого ничего не печатает. Как так:

$ g++ test.cpp -o test.out; ./test.out foo.html 
Filename: foo.html 
Determined filetype: html 
Filename: 

Я вспомнил кое-что о итераторы в прошлом, и попытался с помощью filename.begin(), чтобы сбросить его, но это ничего не делал. Может ли кто-то пролить свет на эту загадочную проблему?

+1

Мы действительно предпочитаем только критические элементы. http://sscce.org/ – chris

+0

Затем пропустите код и просто прочитайте нижнюю часть:] –

ответ

3

Вы объявляете вторую переменную с именем файла здесь, после else:

string filename = argv[1]; 

Это выходит за рамки к тому времени, вы получите здесь:

cout << "Filename: " << filename << endl; 

Вы теперь печать содержимого 1-й переменной, которую вы указали, называется filename, чуть ниже main.

+0

Ах, woah. Это было ослепительно просто, не могу поверить, что это было то, чего я отсутствовал. Благодаря! –

+1

@betaRepeating Обычно у компиляторов есть предупреждение об этом. Всегда следите за тем, чтобы ваша программа строилась без предупреждений и позволяла как можно больше предупреждений. Например, clang и я предполагаю, что gcc будет указывать прямо на эту переменную и сказать что-то вроде «предупреждение: объявление тени локальной переменной», если вы включаете -Wshadow или -Weverything – bames53

Смежные вопросы