首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >试图用向量排序映射值时令人难以理解的错误

试图用向量排序映射值时令人难以理解的错误
EN

Stack Overflow用户
提问于 2021-05-02 00:46:36
回答 2查看 43关注 0票数 0

我有一个WordEntry类,它有一个unordered_map<string, int>,我想存储每个单词的频率。我可以这样做,但我也想向用户显示前5个单词和底部5个单词。要做到这一点,我必须整理一下。但是,我得到了一个非常可怕的、令人讨厌的错误,这个错误与您通常的c++异常不一样。我不知道是否包括在内会有很大帮助,因为它是相当长的。这是我的wordentry.h

代码语言:javascript
复制
#ifndef WORDENTRY_H
#define WORDENTRY_H
#include "node.h"
#include "bst.h"
#include <vector>
#include <unordered_map>
#include <string>
#include <algorithm>
using namespace std;

template <class T>
class WordEntry
{
public:
    int retrieveWordFreq(Node<T> *);
    void collectWords(T data);
    void getTop5();
    void getBot5();
    unordered_map<T, int> freqs;

private:
    int freq = 0;
    bool sortByVal( pair<string, int> &a,  pair<string, int> &b);
};

template <class T>
int WordEntry<T>::retrieveWordFreq(Node<T> *word)
{
}

template <class T>
void WordEntry<T>::getTop5()
{
    vector<pair<string, int>> vec;

    // copy key-value pairs from the map to the vector
    unordered_map<string, int>::iterator it2;
    for (it2 = freqs.begin(); it2 != freqs.end(); it2++)
    {
        vec.push_back(make_pair(it2->first, it2->second));
    }

    // // sort the vector by increasing order of its pair's second value
    sort(vec.begin(), vec.end(), sortByVal);

    for (int i = vec.size() - 1; i > vec.size() - 6; i--)
    {
        cout << vec[i].first << ": " << vec[i].second << endl;
    }
}

template <class T>
void WordEntry<T>::getBot5()
{
    vector<pair<string, int>> vec;

     for (auto& it : freqs) {
        vec.push_back(it);
    }

    
    sort(vec.begin(), vec.end(), sortByVal);

    for (int i = 0; i < 6; i++)
    {
        cout << vec[i].first << ": " << vec[i].second << endl;
    }
}

template <class T>
void WordEntry<T>::collectWords(T val)
{
    freqs[val]++;
}

template <class T>
bool WordEntry<T>::sortByVal(pair<string, int> &a,  pair<string, int> &b)
{
    return (a.second < b.second);
}
#endif

还有我的主菜

代码语言:javascript
复制
#include <iostream>
#include <fstream>
#include <string>
#include <vector>
#include <unordered_set>
#include "bst.h"
#include "wordentry.h"


using namespace std;

int main()
{
    fstream file;
    string word, filename;

    BST<string> wordTree; 
    unordered_set<string> set; 
    WordEntry<string> words; 

    filename = "file.txt";
    file.open(filename.c_str());

    
    while (file >> word)
    {
        wordTree.insert(word); 
        words.collectWords(word); 
    } 
    
    cout << "Words amount: " << wordTree.length() << "\n";
    cout << "Unique Words amount: " << set.size() << "\n"; 
    
    words.getBot5(); 

    int choice; 
    
    cout << "What do you want to do?\n1. Enter a word and find it's frequency\n2.Output frequency analysis to a file\n"; 
    cin >> choice; 
    if (choice == 1) {
        string word; 
        cout << "Enter the word you want the frequency of \n"; 
        cin >> word; 
        for (auto x : words.freqs)
        {
            if (x.first == word)
            {
                cout << x.second; 
            }
        }
    }
    else if (choice == 2)
    {
        ofstream outfile ("output.txt"); 
        outfile << "Words amount: " << wordTree.length() << "\n";
        outfile << "Unique Words amount: " << set.size() << "\n"; 
    }
    
    
   return 0; 
    
}

words.getBot5();是罪魁祸首,这意味着我的实现是错误的,但我不知道为什么。我只是将密钥对复制到向量并进行排序。

编辑:这是错误

代码语言:javascript
复制
In file included from c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_algobase.h:71:0,
                 from c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\char_traits.h:39,
                 from c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\ios:40,
                 from c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\ostream:38,
                 from c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\iostream:39,
                 from driver.cpp:1:
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\predefined_ops.h: In instantiation of 
'constexpr bool __gnu_cxx::__ops::_Iter_comp_iter<_Compare>::operator()(_Iterator1, _Iterator2) [with _Iterator1 = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > 
>; _Iterator2 = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Compare = bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)]':
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_algo.h:1844:14:   required from 'void std::__insertion_sort(_RandomAccessIterator, _RandomAccessIterator, _Compare) [with _RandomAccessIterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; 
_Compare = __gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>]'
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_algo.h:1882:25:   required from 'void std::__final_insertion_sort(_RandomAccessIterator, _RandomAccessIterator, _Compare) [with _RandomAccessIterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Compare = __gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>]'
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_algo.h:1968:31:   required from 'void std::__sort(_RandomAccessIterator, _RandomAccessIterator, _Compare) [with _RandomAccessIterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Compare = __gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>]'
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_algo.h:4739:18:   required from 'void std::sort(_RAIter, _RAIter, _Compare) [with _RAIter = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Compare = bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)]'
wordentry.h:62:9:   required from 'void WordEntry<T>::getBot5() [with T = std::__cxx11::basic_string<char>]'
driver.cpp:34:19:   required from here
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\predefined_ops.h:123:18: error: must use '.*' or '->*' to call pointer-to-member function in '((__gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>*)this)->__gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>::_M_comp (...)', e.g. '(... ->* ((__gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>*)this)->__gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>::_M_comp) (...)'
         { return bool(_M_comp(*__it1, *__it2)); }
                  ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\predefined_ops.h: In instantiation of 
'bool __gnu_cxx::__ops::_Iter_comp_val<_Compare>::operator()(_Iterator, _Value&) [with _Iterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, 
int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Value = std::pair<std::__cxx11::basic_string<char>, int>; _Compare = bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)]':
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_heap.h:129:48:   required from 'void std::__push_heap(_RandomAccessIterator, _Distance, _Distance, _Tp, _Compare) [with 
_RandomAccessIterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Distance = int; _Tp = std::pair<std::__cxx11::basic_string<char>, int>; _Compare = __gnu_cxx::__ops::_Iter_comp_val<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>]'
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_heap.h:230:23:   required from 'void std::__adjust_heap(_RandomAccessIterator, _Distance, _Distance, _Tp, _Compare) [with _RandomAccessIterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; 
_Distance = int; _Tp = std::pair<std::__cxx11::basic_string<char>, int>; _Compare = __gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>]'
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_heap.h:335:22:   required from 'void std::__make_heap(_RandomAccessIterator, _RandomAccessIterator, _Compare) [with _RandomAccessIterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Compare = __gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>]'
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_algo.h:1669:23:   required from 'void std::__heap_select(_RandomAccessIterator, _RandomAccessIterator, _RandomAccessIterator, _Compare) [with _RandomAccessIterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Compare = __gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>]'
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_algo.h:1930:25:   required from 'void std::__partial_sort(_RandomAccessIterator, _RandomAccessIterator, _RandomAccessIterator, _Compare) [with _RandomAccessIterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Compare = __gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, 
std::pair<std::__cxx11::basic_string<char>, int>&)>]'
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_algo.h:1945:27:   required from 'void std::__introsort_loop(_RandomAccessIterator, _RandomAccessIterator, _Size, _Compare) [with _RandomAccessIterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Size = int; _Compare = __gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>]'
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_algo.h:1965:25:   required from 'void std::__sort(_RandomAccessIterator, _RandomAccessIterator, _Compare) [with _RandomAccessIterator = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Compare = __gnu_cxx::__ops::_Iter_comp_iter<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>]'
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\stl_algo.h:4739:18:   required from 'void std::sort(_RAIter, _RAIter, _Compare) [with _RAIter = __gnu_cxx::__normal_iterator<std::pair<std::__cxx11::basic_string<char>, int>*, std::vector<std::pair<std::__cxx11::basic_string<char>, int> > >; _Compare = bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)]'
wordentry.h:62:9:   required from 'void WordEntry<T>::getBot5() [with T = std::__cxx11::basic_string<char>]'
driver.cpp:34:19:   required from here
c:\mingw\lib\gcc\mingw32\6.3.0\include\c++\bits\predefined_ops.h:144:11: error: must use '.*' or '->*' to call pointer-to-member function in '((__gnu_cxx::__ops::_Iter_comp_val<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>*)this)->__gnu_cxx::__ops::_Iter_comp_val<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>::_M_comp (...)', e.g. '(... ->* ((__gnu_cxx::__ops::_Iter_comp_val<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>*)this)->__gnu_cxx::__ops::_Iter_comp_val<bool (WordEntry<std::__cxx11::basic_string<char> >::*)(std::pair<std::__cxx11::basic_string<char>, int>&, std::pair<std::__cxx11::basic_string<char>, int>&)>::_M_comp) (...)'
  { return bool(_M_comp(*__it, __val)); }
           ^~~~~~~~~~~~~~~~~~~~~~~~~~~
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2021-05-02 01:10:33

你需要做一些不同的事情。

首先,您必须使比较器static如下所示:

代码语言:javascript
复制
template <class T>
class WordEntry
{
public:
//    int retrieveWordFreq(Node<T> *);
    void collectWords(T data);
    void getTop5();
    void getBot5();
    unordered_map<T, int> freqs;

private:
    int freq = 0;
   static bool sortByVal( pair<string, int> &a,  pair<string, int> &b); // static
};

因为普通成员函数指针比静态成员函数更复杂,因为它们需要一个对象来操作。

第二,你必须用它的限定名称来称呼它:

代码语言:javascript
复制
sort(vec.begin(), vec.end(), WordEntry<T>::sortByVal); // qualified name
票数 2
EN

Stack Overflow用户

发布于 2021-05-02 03:48:39

可以在不对列表进行排序的情况下完成这一任务,并且运行速度要快得多,特别是对于大型列表。

要获得最大或最小的项,只需扫描一次列表并跟踪一个变量。如果您发现一个比当前最大的条目更大的条目,只需将其复制到最大的条目即可。如果您发现一个比当前最小项更小的条目,只需将其复制到最小项中即可。

给定一个大小为N的数组,下面的伪代码将找到最大或最小的。

代码语言:javascript
复制
Copy = array[0];

foreach Entry in array
  if searching for largest and Entry > Copy, set Copy = Entry
  if searching for smallest and Entry < Copy, set Copy = Entry

当此代码完成时,副本包含最大或最小的副本。此代码的运行时为O(n),而排序第一,取最大或最小的运行时为O(n * lg(n))

对于任何固定大小的K,只需复制一个大小为K的数组。伪代码的变化很小。

首先,我们假设存在一个函数Find_S_or_L_In_Copy(),该函数返回复制数组中最小或最大项的索引。

其次,我们使用这个函数来帮助跟踪最小或最大的K项。

代码语言:javascript
复制
foreach Slot in Copy
  Copy[Slot] = Array[0]

foreach Entry in Array
  if searching for largest K
    set Item = Find_S_or_L_In_Copy()
    if Entry > Copy[Item], set Copy[Item] = Entry

  if searching for smallest K
    set Item = Find_S_or_L_In_Copy()
    if Entry < Copy[Item], set Copy[Item] = Entry

当这些新代码退出时,数组Copy将包含来自ArrayK最大或最小的条目。此代码的运行时为O(N * K)

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/67352068

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档